Commit 56e5e0b6 authored by David Crawshaw's avatar David Crawshaw

runtime: tell race detector about reflectOffs.lock

Fixes #15832

Change-Id: I6f3f45e3c21edd0e093ecb1d8a067907863478f5
Reviewed-on: https://go-review.googlesource.com/23441Reviewed-by: 's avatarDmitry Vyukov <dvyukov@google.com>
parent 6247ca2d
...@@ -5722,3 +5722,18 @@ func TestTypeStrings(t *testing.T) { ...@@ -5722,3 +5722,18 @@ func TestTypeStrings(t *testing.T) {
} }
} }
} }
func TestOffsetLock(t *testing.T) {
var wg sync.WaitGroup
for i := 0; i < 4; i++ {
i := i
wg.Add(1)
go func() {
for j := 0; j < 50; j++ {
ResolveReflectName(fmt.Sprintf("OffsetLockName:%d:%d", i, j))
}
wg.Done()
}()
}
wg.Wait()
}
...@@ -109,3 +109,7 @@ func IsExported(t Type) bool { ...@@ -109,3 +109,7 @@ func IsExported(t Type) bool {
n := typ.nameOff(typ.str) n := typ.nameOff(typ.str)
return n.isExported() return n.isExported()
} }
func ResolveReflectName(s string) {
resolveReflectName(newName(s, "", "", false))
}
...@@ -509,7 +509,7 @@ func reflect_resolveTextOff(rtype unsafe.Pointer, off int32) unsafe.Pointer { ...@@ -509,7 +509,7 @@ func reflect_resolveTextOff(rtype unsafe.Pointer, off int32) unsafe.Pointer {
// reflect_addReflectOff adds a pointer to the reflection offset lookup map. // reflect_addReflectOff adds a pointer to the reflection offset lookup map.
//go:linkname reflect_addReflectOff reflect.addReflectOff //go:linkname reflect_addReflectOff reflect.addReflectOff
func reflect_addReflectOff(ptr unsafe.Pointer) int32 { func reflect_addReflectOff(ptr unsafe.Pointer) int32 {
lock(&reflectOffs.lock) reflectOffsLock()
if reflectOffs.m == nil { if reflectOffs.m == nil {
reflectOffs.m = make(map[int32]unsafe.Pointer) reflectOffs.m = make(map[int32]unsafe.Pointer)
reflectOffs.minv = make(map[unsafe.Pointer]int32) reflectOffs.minv = make(map[unsafe.Pointer]int32)
...@@ -522,6 +522,6 @@ func reflect_addReflectOff(ptr unsafe.Pointer) int32 { ...@@ -522,6 +522,6 @@ func reflect_addReflectOff(ptr unsafe.Pointer) int32 {
reflectOffs.m[id] = ptr reflectOffs.m[id] = ptr
reflectOffs.minv[ptr] = id reflectOffs.minv[ptr] = id
} }
unlock(&reflectOffs.lock) reflectOffsUnlock()
return id return id
} }
...@@ -169,6 +169,20 @@ var reflectOffs struct { ...@@ -169,6 +169,20 @@ var reflectOffs struct {
minv map[unsafe.Pointer]int32 minv map[unsafe.Pointer]int32
} }
func reflectOffsLock() {
lock(&reflectOffs.lock)
if raceenabled {
raceacquire(unsafe.Pointer(&reflectOffs.lock))
}
}
func reflectOffsUnlock() {
if raceenabled {
racerelease(unsafe.Pointer(&reflectOffs.lock))
}
unlock(&reflectOffs.lock)
}
func resolveNameOff(ptrInModule unsafe.Pointer, off nameOff) name { func resolveNameOff(ptrInModule unsafe.Pointer, off nameOff) name {
if off == 0 { if off == 0 {
return name{} return name{}
...@@ -182,9 +196,9 @@ func resolveNameOff(ptrInModule unsafe.Pointer, off nameOff) name { ...@@ -182,9 +196,9 @@ func resolveNameOff(ptrInModule unsafe.Pointer, off nameOff) name {
} }
} }
if md == nil { if md == nil {
lock(&reflectOffs.lock) reflectOffsLock()
res, found := reflectOffs.m[int32(off)] res, found := reflectOffs.m[int32(off)]
unlock(&reflectOffs.lock) reflectOffsUnlock()
if !found { if !found {
println("runtime: nameOff", hex(off), "base", hex(base), "not in ranges:") println("runtime: nameOff", hex(off), "base", hex(base), "not in ranges:")
for next := &firstmoduledata; next != nil; next = next.next { for next := &firstmoduledata; next != nil; next = next.next {
...@@ -219,9 +233,9 @@ func (t *_type) typeOff(off typeOff) *_type { ...@@ -219,9 +233,9 @@ func (t *_type) typeOff(off typeOff) *_type {
} }
} }
if md == nil { if md == nil {
lock(&reflectOffs.lock) reflectOffsLock()
res := reflectOffs.m[int32(off)] res := reflectOffs.m[int32(off)]
unlock(&reflectOffs.lock) reflectOffsUnlock()
if res == nil { if res == nil {
println("runtime: typeOff", hex(off), "base", hex(base), "not in ranges:") println("runtime: typeOff", hex(off), "base", hex(base), "not in ranges:")
for next := &firstmoduledata; next != nil; next = next.next { for next := &firstmoduledata; next != nil; next = next.next {
...@@ -252,9 +266,9 @@ func (t *_type) textOff(off textOff) unsafe.Pointer { ...@@ -252,9 +266,9 @@ func (t *_type) textOff(off textOff) unsafe.Pointer {
} }
} }
if md == nil { if md == nil {
lock(&reflectOffs.lock) reflectOffsLock()
res := reflectOffs.m[int32(off)] res := reflectOffs.m[int32(off)]
unlock(&reflectOffs.lock) reflectOffsUnlock()
if res == nil { if res == nil {
println("runtime: textOff", hex(off), "base", hex(base), "not in ranges:") println("runtime: textOff", hex(off), "base", hex(base), "not in ranges:")
for next := &firstmoduledata; next != nil; next = next.next { for next := &firstmoduledata; next != nil; next = next.next {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment