1 // Copyright 2015 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 package runtime_test 6 7 import ( 8 "runtime" 9 "testing" 10 "unsafe" 11 ) 12 13 func runParallel(N, iter int, f func()) { 14 defer runtime.GOMAXPROCS(runtime.GOMAXPROCS(int(N))) 15 done := make(chan bool) 16 for i := 0; i < N; i++ { 17 go func() { 18 for j := 0; j < iter; j++ { 19 f() 20 } 21 done <- true 22 }() 23 } 24 for i := 0; i < N; i++ { 25 <-done 26 } 27 } 28 29 func TestXadduintptr(t *testing.T) { 30 const N = 20 31 const iter = 100000 32 inc := uintptr(100) 33 total := uintptr(0) 34 runParallel(N, iter, func() { 35 runtime.Xadduintptr(&total, inc) 36 }) 37 if want := uintptr(N * iter * inc); want != total { 38 t.Fatalf("xadduintpr error, want %d, got %d", want, total) 39 } 40 total = 0 41 runParallel(N, iter, func() { 42 runtime.Xadduintptr(&total, inc) 43 runtime.Xadduintptr(&total, uintptr(-int64(inc))) 44 }) 45 if total != 0 { 46 t.Fatalf("xadduintpr total error, want %d, got %d", 0, total) 47 } 48 } 49 50 // Tests that xadduintptr correctly updates 64-bit values. The place where 51 // we actually do so is mstats.go, functions mSysStat{Inc,Dec}. 52 func TestXadduintptrOnUint64(t *testing.T) { 53 if runtime.BigEndian != 0 { 54 // On big endian architectures, we never use xadduintptr to update 55 // 64-bit values and hence we skip the test. (Note that functions 56 // mSysStat{Inc,Dec} in mstats.go have explicit checks for 57 // big-endianness.) 58 return 59 } 60 const inc = 100 61 val := uint64(0) 62 runtime.Xadduintptr((*uintptr)(unsafe.Pointer(&val)), inc) 63 if inc != val { 64 t.Fatalf("xadduintptr should increase lower-order bits, want %d, got %d", inc, val) 65 } 66 } 67