github.com/cockroachdb/tools@v0.0.0-20230222021103-a6d27438930d/go/analysis/passes/copylock/testdata/src/a/copylock.go (about) 1 package a 2 3 import ( 4 "sync" 5 "sync/atomic" 6 "unsafe" 7 . "unsafe" 8 unsafe1 "unsafe" 9 ) 10 11 func OkFunc() { 12 var x *sync.Mutex 13 p := x 14 var y sync.Mutex 15 p = &y 16 17 var z = sync.Mutex{} 18 w := sync.Mutex{} 19 20 w = sync.Mutex{} 21 q := struct{ L sync.Mutex }{ 22 L: sync.Mutex{}, 23 } 24 25 yy := []Tlock{ 26 Tlock{}, 27 Tlock{ 28 once: sync.Once{}, 29 }, 30 } 31 32 nl := new(sync.Mutex) 33 mx := make([]sync.Mutex, 10) 34 xx := struct{ L *sync.Mutex }{ 35 L: new(sync.Mutex), 36 } 37 } 38 39 type Tlock struct { 40 once sync.Once 41 } 42 43 func BadFunc() { 44 var x *sync.Mutex 45 p := x 46 var y sync.Mutex 47 p = &y 48 *p = *x // want `assignment copies lock value to \*p: sync.Mutex` 49 50 var t Tlock 51 var tp *Tlock 52 tp = &t 53 *tp = t // want `assignment copies lock value to \*tp: a.Tlock contains sync.Once contains sync\b.*` 54 t = *tp // want `assignment copies lock value to t: a.Tlock contains sync.Once contains sync\b.*` 55 56 y := *x // want "assignment copies lock value to y: sync.Mutex" 57 var z = t // want `variable declaration copies lock value to z: a.Tlock contains sync.Once contains sync\b.*` 58 59 w := struct{ L sync.Mutex }{ 60 L: *x, // want `literal copies lock value from \*x: sync.Mutex` 61 } 62 var q = map[int]Tlock{ 63 1: t, // want `literal copies lock value from t: a.Tlock contains sync.Once contains sync\b.*` 64 2: *tp, // want `literal copies lock value from \*tp: a.Tlock contains sync.Once contains sync\b.*` 65 } 66 yy := []Tlock{ 67 t, // want `literal copies lock value from t: a.Tlock contains sync.Once contains sync\b.*` 68 *tp, // want `literal copies lock value from \*tp: a.Tlock contains sync.Once contains sync\b.*` 69 } 70 71 // override 'new' keyword 72 new := func(interface{}) {} 73 new(t) // want `call of new copies lock value: a.Tlock contains sync.Once contains sync\b.*` 74 75 // copy of array of locks 76 var muA [5]sync.Mutex 77 muB := muA // want "assignment copies lock value to muB: sync.Mutex" 78 muA = muB // want "assignment copies lock value to muA: sync.Mutex" 79 muSlice := muA[:] // OK 80 81 // multidimensional array 82 var mmuA [5][5]sync.Mutex 83 mmuB := mmuA // want "assignment copies lock value to mmuB: sync.Mutex" 84 mmuA = mmuB // want "assignment copies lock value to mmuA: sync.Mutex" 85 mmuSlice := mmuA[:] // OK 86 87 // slice copy is ok 88 var fmuA [5][][5]sync.Mutex 89 fmuB := fmuA // OK 90 fmuA = fmuB // OK 91 fmuSlice := fmuA[:] // OK 92 93 // map access by single and tuple copies prohibited 94 type mut struct{ mu sync.Mutex } 95 muM := map[string]mut{ 96 "a": mut{}, 97 } 98 mumA := muM["a"] // want "assignment copies lock value to mumA: a.mut contains sync.Mutex" 99 mumB, _ := muM["a"] // want "assignment copies lock value to mumB: \\(a.mut, bool\\) contains a.mut contains sync.Mutex" 100 } 101 102 func LenAndCapOnLockArrays() { 103 var a [5]sync.Mutex 104 aLen := len(a) // OK 105 aCap := cap(a) // OK 106 107 // override 'len' and 'cap' keywords 108 109 len := func(interface{}) {} 110 len(a) // want "call of len copies lock value: sync.Mutex" 111 112 cap := func(interface{}) {} 113 cap(a) // want "call of cap copies lock value: sync.Mutex" 114 } 115 116 func SizeofMutex() { 117 var mu sync.Mutex 118 unsafe.Sizeof(mu) // OK 119 unsafe1.Sizeof(mu) // OK 120 Sizeof(mu) // OK 121 unsafe := struct{ Sizeof func(interface{}) }{} 122 unsafe.Sizeof(mu) // want "call of unsafe.Sizeof copies lock value: sync.Mutex" 123 Sizeof := func(interface{}) {} 124 Sizeof(mu) // want "call of Sizeof copies lock value: sync.Mutex" 125 } 126 127 func OffsetofMutex() { 128 type T struct { 129 f int 130 mu sync.Mutex 131 } 132 unsafe.Offsetof(T{}.mu) // OK 133 unsafe := struct{ Offsetof func(interface{}) }{} 134 unsafe.Offsetof(T{}.mu) // want "call of unsafe.Offsetof copies lock value: sync.Mutex" 135 } 136 137 func AlignofMutex() { 138 type T struct { 139 f int 140 mu sync.Mutex 141 } 142 unsafe.Alignof(T{}.mu) // OK 143 unsafe := struct{ Alignof func(interface{}) }{} 144 unsafe.Alignof(T{}.mu) // want "call of unsafe.Alignof copies lock value: sync.Mutex" 145 } 146 147 // SyncTypesCheck checks copying of sync.* types except sync.Mutex 148 func SyncTypesCheck() { 149 // sync.RWMutex copying 150 var rwmuX sync.RWMutex 151 var rwmuXX = sync.RWMutex{} 152 rwmuX1 := new(sync.RWMutex) 153 rwmuY := rwmuX // want "assignment copies lock value to rwmuY: sync.RWMutex" 154 rwmuY = rwmuX // want "assignment copies lock value to rwmuY: sync.RWMutex" 155 var rwmuYY = rwmuX // want "variable declaration copies lock value to rwmuYY: sync.RWMutex" 156 rwmuP := &rwmuX 157 rwmuZ := &sync.RWMutex{} 158 159 // sync.Cond copying 160 var condX sync.Cond 161 var condXX = sync.Cond{} 162 condX1 := new(sync.Cond) 163 condY := condX // want "assignment copies lock value to condY: sync.Cond contains sync.noCopy" 164 condY = condX // want "assignment copies lock value to condY: sync.Cond contains sync.noCopy" 165 var condYY = condX // want "variable declaration copies lock value to condYY: sync.Cond contains sync.noCopy" 166 condP := &condX 167 condZ := &sync.Cond{ 168 L: &sync.Mutex{}, 169 } 170 condZ = sync.NewCond(&sync.Mutex{}) 171 172 // sync.WaitGroup copying 173 var wgX sync.WaitGroup 174 var wgXX = sync.WaitGroup{} 175 wgX1 := new(sync.WaitGroup) 176 wgY := wgX // want "assignment copies lock value to wgY: sync.WaitGroup contains sync.noCopy" 177 wgY = wgX // want "assignment copies lock value to wgY: sync.WaitGroup contains sync.noCopy" 178 var wgYY = wgX // want "variable declaration copies lock value to wgYY: sync.WaitGroup contains sync.noCopy" 179 wgP := &wgX 180 wgZ := &sync.WaitGroup{} 181 182 // sync.Pool copying 183 var poolX sync.Pool 184 var poolXX = sync.Pool{} 185 poolX1 := new(sync.Pool) 186 poolY := poolX // want "assignment copies lock value to poolY: sync.Pool contains sync.noCopy" 187 poolY = poolX // want "assignment copies lock value to poolY: sync.Pool contains sync.noCopy" 188 var poolYY = poolX // want "variable declaration copies lock value to poolYY: sync.Pool contains sync.noCopy" 189 poolP := &poolX 190 poolZ := &sync.Pool{} 191 192 // sync.Once copying 193 var onceX sync.Once 194 var onceXX = sync.Once{} 195 onceX1 := new(sync.Once) 196 onceY := onceX // want `assignment copies lock value to onceY: sync.Once contains sync\b.*` 197 onceY = onceX // want `assignment copies lock value to onceY: sync.Once contains sync\b.*` 198 var onceYY = onceX // want `variable declaration copies lock value to onceYY: sync.Once contains sync\b.*` 199 onceP := &onceX 200 onceZ := &sync.Once{} 201 } 202 203 // AtomicTypesCheck checks copying of sync/atomic types 204 func AtomicTypesCheck() { 205 // atomic.Value copying 206 var vX atomic.Value 207 var vXX = atomic.Value{} 208 vX1 := new(atomic.Value) 209 // These are OK because the value has not been used yet. 210 // (And vet can't tell whether it has been used, so they're always OK.) 211 vY := vX 212 vY = vX 213 var vYY = vX 214 vP := &vX 215 vZ := &atomic.Value{} 216 }