summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorR?my Oudompheng <oudomphe@phare.normalesup.org>2012-02-06 19:16:26 +0100
committerR?my Oudompheng <oudomphe@phare.normalesup.org>2012-02-06 19:16:26 +0100
commit71f9a05e783532e348b78ac6696a9bd2b64c90d6 (patch)
tree21b5b46e4adf5b7fd3e5753ccb3dcddbd20ede67
parenta899195ae7479be02c2d4212f316698e123b471c (diff)
downloadgo-71f9a05e783532e348b78ac6696a9bd2b64c90d6.tar.gz
runtime: delete UpdateMemStats, replace with ReadMemStats(&stats).
Unexports runtime.MemStats and rename MemStatsType to MemStats. The new accessor requires passing a pointer to a user-allocated MemStats structure. Fixes issue 2572. R=bradfitz, rsc, bradfitz, gustavo CC=golang-dev, remy http://codereview.appspot.com/5616072
-rw-r--r--src/cmd/godoc/godoc.go7
-rw-r--r--src/pkg/encoding/gob/timing_test.go18
-rw-r--r--src/pkg/expvar/expvar.go4
-rw-r--r--src/pkg/fmt/fmt_test.go9
-rw-r--r--src/pkg/net/rpc/server_test.go9
-rw-r--r--src/pkg/reflect/all_test.go10
-rw-r--r--src/pkg/runtime/gc_test.go11
-rw-r--r--src/pkg/runtime/malloc.h2
-rw-r--r--src/pkg/runtime/mem.go21
-rw-r--r--src/pkg/runtime/mgc0.c3
-rw-r--r--src/pkg/runtime/pprof/pprof.go3
-rw-r--r--src/pkg/strconv/itoa_test.go9
-rw-r--r--test/bench/garbage/parser.go20
-rw-r--r--test/bench/garbage/stats.go3
-rw-r--r--test/bench/garbage/tree2.go15
-rw-r--r--test/chan/select2.go9
-rw-r--r--test/closure.go11
-rw-r--r--test/gc2.go8
-rw-r--r--test/init1.go14
-rw-r--r--test/malloc1.go5
-rw-r--r--test/mallocrand.go5
-rw-r--r--test/mallocrep.go24
-rw-r--r--test/mallocrep1.go14
23 files changed, 129 insertions, 105 deletions
diff --git a/src/cmd/godoc/godoc.go b/src/cmd/godoc/godoc.go
index 34e058ab5..5745b28ba 100644
--- a/src/cmd/godoc/godoc.go
+++ b/src/cmd/godoc/godoc.go
@@ -1510,9 +1510,12 @@ func updateIndex() {
log.Printf("index updated (%gs, %d bytes of source, %d files, %d lines, %d unique words, %d spots)",
secs, stats.Bytes, stats.Files, stats.Lines, stats.Words, stats.Spots)
}
- log.Printf("before GC: bytes = %d footprint = %d", runtime.MemStats.HeapAlloc, runtime.MemStats.Sys)
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ log.Printf("before GC: bytes = %d footprint = %d", memstats.HeapAlloc, memstats.Sys)
runtime.GC()
- log.Printf("after GC: bytes = %d footprint = %d", runtime.MemStats.HeapAlloc, runtime.MemStats.Sys)
+ runtime.ReadMemStats(memstats)
+ log.Printf("after GC: bytes = %d footprint = %d", memstats.HeapAlloc, memstats.Sys)
}
func indexer() {
diff --git a/src/pkg/encoding/gob/timing_test.go b/src/pkg/encoding/gob/timing_test.go
index 1017eb7f5..b9371c423 100644
--- a/src/pkg/encoding/gob/timing_test.go
+++ b/src/pkg/encoding/gob/timing_test.go
@@ -53,8 +53,9 @@ func TestCountEncodeMallocs(t *testing.T) {
var buf bytes.Buffer
enc := NewEncoder(&buf)
bench := &Bench{7, 3.2, "now is the time", []byte("for all good men")}
- runtime.UpdateMemStats()
- mallocs := 0 - runtime.MemStats.Mallocs
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ mallocs := 0 - memstats.Mallocs
const count = 1000
for i := 0; i < count; i++ {
err := enc.Encode(bench)
@@ -62,8 +63,8 @@ func TestCountEncodeMallocs(t *testing.T) {
t.Fatal("encode:", err)
}
}
- runtime.UpdateMemStats()
- mallocs += runtime.MemStats.Mallocs
+ runtime.ReadMemStats(memstats)
+ mallocs += memstats.Mallocs
fmt.Printf("mallocs per encode of type Bench: %d\n", mallocs/count)
}
@@ -79,8 +80,9 @@ func TestCountDecodeMallocs(t *testing.T) {
}
}
dec := NewDecoder(&buf)
- runtime.UpdateMemStats()
- mallocs := 0 - runtime.MemStats.Mallocs
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ mallocs := 0 - memstats.Mallocs
for i := 0; i < count; i++ {
*bench = Bench{}
err := dec.Decode(&bench)
@@ -88,7 +90,7 @@ func TestCountDecodeMallocs(t *testing.T) {
t.Fatal("decode:", err)
}
}
- runtime.UpdateMemStats()
- mallocs += runtime.MemStats.Mallocs
+ runtime.ReadMemStats(memstats)
+ mallocs += memstats.Mallocs
fmt.Printf("mallocs per decode of type Bench: %d\n", mallocs/count)
}
diff --git a/src/pkg/expvar/expvar.go b/src/pkg/expvar/expvar.go
index ee32eff9e..0ccfb3432 100644
--- a/src/pkg/expvar/expvar.go
+++ b/src/pkg/expvar/expvar.go
@@ -277,7 +277,9 @@ func cmdline() interface{} {
}
func memstats() interface{} {
- return runtime.MemStats
+ stats := new(runtime.MemStats)
+ runtime.ReadMemStats(stats)
+ return *stats
}
func init() {
diff --git a/src/pkg/fmt/fmt_test.go b/src/pkg/fmt/fmt_test.go
index cd0b0ce66..44dcae46c 100644
--- a/src/pkg/fmt/fmt_test.go
+++ b/src/pkg/fmt/fmt_test.go
@@ -538,13 +538,14 @@ var _ bytes.Buffer
func TestCountMallocs(t *testing.T) {
for _, mt := range mallocTest {
const N = 100
- runtime.UpdateMemStats()
- mallocs := 0 - runtime.MemStats.Mallocs
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ mallocs := 0 - memstats.Mallocs
for i := 0; i < N; i++ {
mt.fn()
}
- runtime.UpdateMemStats()
- mallocs += runtime.MemStats.Mallocs
+ runtime.ReadMemStats(memstats)
+ mallocs += memstats.Mallocs
if mallocs/N > uint64(mt.count) {
t.Errorf("%s: expected %d mallocs, got %d", mt.desc, mt.count, mallocs/N)
}
diff --git a/src/pkg/net/rpc/server_test.go b/src/pkg/net/rpc/server_test.go
index b05c63c05..8cfa033cc 100644
--- a/src/pkg/net/rpc/server_test.go
+++ b/src/pkg/net/rpc/server_test.go
@@ -442,8 +442,9 @@ func countMallocs(dial func() (*Client, error), t *testing.T) uint64 {
}
args := &Args{7, 8}
reply := new(Reply)
- runtime.UpdateMemStats()
- mallocs := 0 - runtime.MemStats.Mallocs
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ mallocs := 0 - memstats.Mallocs
const count = 100
for i := 0; i < count; i++ {
err := client.Call("Arith.Add", args, reply)
@@ -454,8 +455,8 @@ func countMallocs(dial func() (*Client, error), t *testing.T) uint64 {
t.Errorf("Add: expected %d got %d", reply.C, args.A+args.B)
}
}
- runtime.UpdateMemStats()
- mallocs += runtime.MemStats.Mallocs
+ runtime.ReadMemStats(memstats)
+ mallocs += memstats.Mallocs
return mallocs / count
}
diff --git a/src/pkg/reflect/all_test.go b/src/pkg/reflect/all_test.go
index 8ae977912..ad9958755 100644
--- a/src/pkg/reflect/all_test.go
+++ b/src/pkg/reflect/all_test.go
@@ -1545,15 +1545,19 @@ func TestAddr(t *testing.T) {
func noAlloc(t *testing.T, n int, f func(int)) {
// once to prime everything
f(-1)
- runtime.MemStats.Mallocs = 0
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ oldmallocs := memstats.Mallocs
for j := 0; j < n; j++ {
f(j)
}
// A few allocs may happen in the testing package when GOMAXPROCS > 1, so don't
// require zero mallocs.
- if runtime.MemStats.Mallocs > 5 {
- t.Fatalf("%d mallocs after %d iterations", runtime.MemStats.Mallocs, n)
+ runtime.ReadMemStats(memstats)
+ mallocs := memstats.Mallocs - oldmallocs
+ if mallocs > 5 {
+ t.Fatalf("%d mallocs after %d iterations", mallocs, n)
}
}
diff --git a/src/pkg/runtime/gc_test.go b/src/pkg/runtime/gc_test.go
index 00b3a04ce..739ebcba2 100644
--- a/src/pkg/runtime/gc_test.go
+++ b/src/pkg/runtime/gc_test.go
@@ -10,20 +10,21 @@ import (
)
func TestGcSys(t *testing.T) {
+ memstats := new(runtime.MemStats)
runtime.GC()
- runtime.UpdateMemStats()
- sys := runtime.MemStats.Sys
+ runtime.ReadMemStats(memstats)
+ sys := memstats.Sys
for i := 0; i < 1000000; i++ {
workthegc()
}
// Should only be using a few MB.
- runtime.UpdateMemStats()
- if sys > runtime.MemStats.Sys {
+ runtime.ReadMemStats(memstats)
+ if sys > memstats.Sys {
sys = 0
} else {
- sys = runtime.MemStats.Sys - sys
+ sys = memstats.Sys - sys
}
t.Logf("used %d extra bytes", sys)
if sys > 4<<20 {
diff --git a/src/pkg/runtime/malloc.h b/src/pkg/runtime/malloc.h
index a85e1af8c..d79c86d12 100644
--- a/src/pkg/runtime/malloc.h
+++ b/src/pkg/runtime/malloc.h
@@ -234,7 +234,7 @@ struct MStats
} by_size[NumSizeClasses];
};
-#define mstats runtime·MemStats /* name shared with Go */
+#define mstats runtime·memStats /* name shared with Go */
extern MStats mstats;
diff --git a/src/pkg/runtime/mem.go b/src/pkg/runtime/mem.go
index 93d155a7f..3ad906ac2 100644
--- a/src/pkg/runtime/mem.go
+++ b/src/pkg/runtime/mem.go
@@ -6,9 +6,9 @@ package runtime
import "unsafe"
-type MemStatsType struct {
+// A MemStats records statistics about the memory allocator.
+type MemStats struct {
// General statistics.
- // Not locked during update; approximate.
Alloc uint64 // bytes allocated and still in use
TotalAlloc uint64 // bytes allocated (even if freed)
Sys uint64 // bytes obtained from system (should be sum of XxxSys below)
@@ -43,7 +43,6 @@ type MemStatsType struct {
DebugGC bool
// Per-size allocation statistics.
- // Not locked during update; approximate.
// 61 is NumSizeClasses in the C code.
BySize [61]struct {
Size uint32
@@ -54,21 +53,17 @@ type MemStatsType struct {
var sizeof_C_MStats uintptr // filled in by malloc.goc
+var memStats MemStats
+
func init() {
- if sizeof_C_MStats != unsafe.Sizeof(MemStats) {
- println(sizeof_C_MStats, unsafe.Sizeof(MemStats))
+ if sizeof_C_MStats != unsafe.Sizeof(memStats) {
+ println(sizeof_C_MStats, unsafe.Sizeof(memStats))
panic("MStats vs MemStatsType size mismatch")
}
}
-// MemStats holds statistics about the memory system.
-// The statistics may be out of date, as the information is
-// updated lazily from per-thread caches.
-// Use UpdateMemStats to bring the statistics up to date.
-var MemStats MemStatsType
-
-// UpdateMemStats brings MemStats up to date.
-func UpdateMemStats()
+// ReadMemStats populates m with memory allocator statistics.
+func ReadMemStats(m *MemStats)
// GC runs a garbage collection.
func GC()
diff --git a/src/pkg/runtime/mgc0.c b/src/pkg/runtime/mgc0.c
index 78daa7836..1b959286a 100644
--- a/src/pkg/runtime/mgc0.c
+++ b/src/pkg/runtime/mgc0.c
@@ -997,7 +997,7 @@ runtime·gc(int32 force)
}
void
-runtime·UpdateMemStats(void)
+runtime·ReadMemStats(MStats *stats)
{
// Have to acquire gcsema to stop the world,
// because stoptheworld can only be used by
@@ -1007,6 +1007,7 @@ runtime·UpdateMemStats(void)
m->gcing = 1;
runtime·stoptheworld();
cachestats();
+ *stats = mstats;
m->gcing = 0;
runtime·semrelease(&gcsema);
runtime·starttheworld(false);
diff --git a/src/pkg/runtime/pprof/pprof.go b/src/pkg/runtime/pprof/pprof.go
index d14bb141c..a8e78e0ea 100644
--- a/src/pkg/runtime/pprof/pprof.go
+++ b/src/pkg/runtime/pprof/pprof.go
@@ -75,7 +75,8 @@ func WriteHeapProfile(w io.Writer) error {
// Print memstats information too.
// Pprof will ignore, but useful for people.
- s := &runtime.MemStats
+ s := new(runtime.MemStats)
+ runtime.ReadMemStats(s)
fmt.Fprintf(b, "\n# runtime.MemStats\n")
fmt.Fprintf(b, "# Alloc = %d\n", s.Alloc)
fmt.Fprintf(b, "# TotalAlloc = %d\n", s.TotalAlloc)
diff --git a/src/pkg/strconv/itoa_test.go b/src/pkg/strconv/itoa_test.go
index d4b09a5d8..6687314d2 100644
--- a/src/pkg/strconv/itoa_test.go
+++ b/src/pkg/strconv/itoa_test.go
@@ -127,11 +127,12 @@ func TestUitoa(t *testing.T) {
}
func numAllocations(f func()) int {
- runtime.UpdateMemStats()
- n0 := runtime.MemStats.Mallocs
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ n0 := memstats.Mallocs
f()
- runtime.UpdateMemStats()
- return int(runtime.MemStats.Mallocs - n0)
+ runtime.ReadMemStats(memstats)
+ return int(memstats.Mallocs - n0)
}
var globalBuf [64]byte
diff --git a/test/bench/garbage/parser.go b/test/bench/garbage/parser.go
index 9e15f6c0f..d66281b6b 100644
--- a/test/bench/garbage/parser.go
+++ b/test/bench/garbage/parser.go
@@ -73,7 +73,7 @@ func parseDir(dirpath string) map[string]*ast.Package {
}
func main() {
- st := &runtime.MemStats
+ st := new(runtime.MemStats)
packages = append(packages, packages...)
packages = append(packages, packages...)
n := flag.Int("n", 4, "iterations")
@@ -83,14 +83,17 @@ func main() {
var lastParsed []map[string]*ast.Package
var t0 time.Time
+ var numGC uint32
+ var pauseTotalNs uint64
pkgroot := runtime.GOROOT() + "/src/pkg/"
for pass := 0; pass < 2; pass++ {
// Once the heap is grown to full size, reset counters.
// This hides the start-up pauses, which are much smaller
// than the normal pauses and would otherwise make
// the average look much better than it actually is.
- st.NumGC = 0
- st.PauseTotalNs = 0
+ runtime.ReadMemStats(st)
+ numGC = st.NumGC
+ pauseTotalNs = st.PauseTotalNs
t0 = time.Now()
for i := 0; i < *n; i++ {
@@ -107,6 +110,9 @@ func main() {
}
t1 := time.Now()
+ runtime.ReadMemStats(st)
+ st.NumGC -= numGC
+ st.PauseTotalNs -= pauseTotalNs
fmt.Printf("Alloc=%d/%d Heap=%d Mallocs=%d PauseTime=%.3f/%d = %.3f\n",
st.Alloc, st.TotalAlloc,
st.Sys,
@@ -142,9 +148,7 @@ var packages = []string{
"container/list",
"container/ring",
"crypto/aes",
- "crypto/blowfish",
"crypto/hmac",
- "crypto/md4",
"crypto/md5",
"crypto/rand",
"crypto/rc4",
@@ -155,7 +159,6 @@ var packages = []string{
"crypto/subtle",
"crypto/tls",
"crypto/x509",
- "crypto/xtea",
"debug/dwarf",
"debug/macho",
"debug/elf",
@@ -164,7 +167,6 @@ var packages = []string{
"encoding/ascii85",
"encoding/base64",
"encoding/binary",
- "encoding/git85",
"encoding/hex",
"encoding/pem",
"os/exec",
@@ -193,8 +195,7 @@ var packages = []string{
"mime",
"net",
"os",
- "os/signal",
- "patch",
+ "exp/signal",
"path",
"math/rand",
"reflect",
@@ -219,6 +220,5 @@ var packages = []string{
"unicode",
"unicode/utf8",
"unicode/utf16",
- "websocket",
"encoding/xml",
}
diff --git a/test/bench/garbage/stats.go b/test/bench/garbage/stats.go
index 985e7eaf5..cdcb32f9b 100644
--- a/test/bench/garbage/stats.go
+++ b/test/bench/garbage/stats.go
@@ -12,7 +12,8 @@ import (
)
func gcstats(name string, n int, t time.Duration) {
- st := &runtime.MemStats
+ st := new(runtime.MemStats)
+ runtime.ReadMemStats(st)
fmt.Printf("garbage.%sMem Alloc=%d/%d Heap=%d NextGC=%d Mallocs=%d\n", name, st.Alloc, st.TotalAlloc, st.Sys, st.NextGC, st.Mallocs)
fmt.Printf("garbage.%s %d %d ns/op\n", name, n, t.Nanoseconds()/int64(n))
fmt.Printf("garbage.%sLastPause 1 %d ns/op\n", name, st.PauseNs[(st.NumGC-1)%uint32(len(st.PauseNs))])
diff --git a/test/bench/garbage/tree2.go b/test/bench/garbage/tree2.go
index 6d78f72c5..3db0a0ba3 100644
--- a/test/bench/garbage/tree2.go
+++ b/test/bench/garbage/tree2.go
@@ -30,6 +30,7 @@ var (
heap *Object
calls [20]int
numobjects int64
+ memstats runtime.MemStats
)
func buildHeap() {
@@ -55,10 +56,10 @@ func buildTree(objsize, size float64, depth int) (*Object, float64) {
func gc() {
runtime.GC()
- runtime.UpdateMemStats()
- pause := runtime.MemStats.PauseTotalNs
- inuse := runtime.MemStats.Alloc
- free := runtime.MemStats.TotalAlloc - inuse
+ runtime.ReadMemStats(&memstats)
+ pause := memstats.PauseTotalNs
+ inuse := memstats.Alloc
+ free := memstats.TotalAlloc - inuse
fmt.Printf("gc pause: %8.3f ms; collect: %8.0f MB; heapsize: %8.0f MB\n",
float64(pause-lastPauseNs)/1e6,
float64(free-lastFree)/1048576,
@@ -71,9 +72,9 @@ func main() {
flag.Parse()
buildHeap()
runtime.GOMAXPROCS(*cpus)
- runtime.UpdateMemStats()
- lastPauseNs = runtime.MemStats.PauseTotalNs
- lastFree = runtime.MemStats.TotalAlloc - runtime.MemStats.Alloc
+ runtime.ReadMemStats(&memstats)
+ lastPauseNs = memstats.PauseTotalNs
+ lastFree = memstats.TotalAlloc - memstats.Alloc
if *cpuprofile != "" {
f, err := os.Create(*cpuprofile)
if err != nil {
diff --git a/test/chan/select2.go b/test/chan/select2.go
index e24c51ed1..2cbb86ec6 100644
--- a/test/chan/select2.go
+++ b/test/chan/select2.go
@@ -35,14 +35,17 @@ func main() {
go sender(c, 100000)
receiver(c, dummy, 100000)
runtime.GC()
- runtime.MemStats.Alloc = 0
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ alloc := memstats.Alloc
// second time shouldn't increase footprint by much
go sender(c, 100000)
receiver(c, dummy, 100000)
runtime.GC()
+ runtime.ReadMemStats(memstats)
- if runtime.MemStats.Alloc > 1e5 {
- println("BUG: too much memory for 100,000 selects:", runtime.MemStats.Alloc)
+ if memstats.Alloc-alloc > 1e5 {
+ println("BUG: too much memory for 100,000 selects:", memstats.Alloc-alloc)
}
}
diff --git a/test/closure.go b/test/closure.go
index 97da1dd23..c2248d68e 100644
--- a/test/closure.go
+++ b/test/closure.go
@@ -92,8 +92,9 @@ func main() {
go h()
check([]int{100, 200, 101, 201, 500, 101, 201, 500})
- runtime.UpdateMemStats()
- n0 := runtime.MemStats.Mallocs
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ n0 := memstats.Mallocs
x, y := newfunc(), newfunc()
if x(1) != 1 || y(2) != 2 {
@@ -101,8 +102,8 @@ func main() {
fail = true
}
- runtime.UpdateMemStats()
- if n0 != runtime.MemStats.Mallocs {
+ runtime.ReadMemStats(memstats)
+ if n0 != memstats.Mallocs {
println("newfunc allocated unexpectedly")
fail = true
}
@@ -110,7 +111,7 @@ func main() {
ff(1)
if fail {
- panic("fail")
+ panic("fail")
}
}
diff --git a/test/gc2.go b/test/gc2.go
index c54d807df..772f9810d 100644
--- a/test/gc2.go
+++ b/test/gc2.go
@@ -19,7 +19,9 @@ import (
func main() {
const N = 10000
- st := runtime.MemStats
+ st := new(runtime.MemStats)
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(st)
for i := 0; i < N; i++ {
c := make(chan int, 10)
_ = c
@@ -33,8 +35,8 @@ func main() {
}
}
- runtime.UpdateMemStats()
- obj := runtime.MemStats.HeapObjects - st.HeapObjects
+ runtime.ReadMemStats(memstats)
+ obj := memstats.HeapObjects - st.HeapObjects
if obj > N/5 {
fmt.Println("too many objects left:", obj)
os.Exit(1)
diff --git a/test/init1.go b/test/init1.go
index 9ce3c12ee..56ef17249 100644
--- a/test/init1.go
+++ b/test/init1.go
@@ -16,10 +16,11 @@ func init() {
c := make(chan int)
go send(c)
<-c
-
- const chunk = 1<<20
- runtime.UpdateMemStats()
- sys := runtime.MemStats.Sys
+
+ const chunk = 1 << 20
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ sys := memstats.Sys
b := make([]byte, chunk)
for i := range b {
b[i] = byte(i%10 + '0')
@@ -28,8 +29,8 @@ func init() {
for i := 0; i < 1000; i++ {
x = []byte(s)
}
- runtime.UpdateMemStats()
- sys1 := runtime.MemStats.Sys
+ runtime.ReadMemStats(memstats)
+ sys1 := memstats.Sys
if sys1-sys > chunk*50 {
println("allocated 1000 chunks of", chunk, "and used ", sys1-sys, "memory")
}
@@ -41,4 +42,3 @@ func send(c chan int) {
func main() {
}
-
diff --git a/test/malloc1.go b/test/malloc1.go
index 61f1797c7..0f7f0b267 100644
--- a/test/malloc1.go
+++ b/test/malloc1.go
@@ -17,9 +17,10 @@ import (
var chatty = flag.Bool("v", false, "chatty")
func main() {
+ memstats := new(runtime.MemStats)
runtime.Free(runtime.Alloc(1))
- runtime.UpdateMemStats()
+ runtime.ReadMemStats(memstats)
if *chatty {
- fmt.Printf("%+v %v\n", runtime.MemStats, uint64(0))
+ fmt.Printf("%+v %v\n", memstats, uint64(0))
}
}
diff --git a/test/mallocrand.go b/test/mallocrand.go
index 726e36799..69d07cec5 100644
--- a/test/mallocrand.go
+++ b/test/mallocrand.go
@@ -21,8 +21,9 @@ var footprint uint64
var allocated uint64
func bigger() {
- runtime.UpdateMemStats()
- if f := runtime.MemStats.Sys; footprint < f {
+ memstats := new(runtime.MemStats)
+ runtime.ReadMemStats(memstats)
+ if f := memstats.Sys; footprint < f {
footprint = f
if *chatty {
println("Footprint", footprint, " for ", allocated)
diff --git a/test/mallocrep.go b/test/mallocrep.go
index cffcd1638..4188da9b8 100644
--- a/test/mallocrep.go
+++ b/test/mallocrep.go
@@ -16,10 +16,12 @@ import (
var chatty = flag.Bool("v", false, "chatty")
var oldsys uint64
+var memstats runtime.MemStats
func bigger() {
- runtime.UpdateMemStats()
- if st := runtime.MemStats; oldsys < st.Sys {
+ st := &memstats
+ runtime.ReadMemStats(st)
+ if oldsys < st.Sys {
oldsys = st.Sys
if *chatty {
println(st.Sys, " system bytes for ", st.Alloc, " Go bytes")
@@ -32,26 +34,26 @@ func bigger() {
}
func main() {
- runtime.GC() // clean up garbage from init
- runtime.UpdateMemStats() // first call can do some allocations
- runtime.MemProfileRate = 0 // disable profiler
- runtime.MemStats.Alloc = 0 // ignore stacks
+ runtime.GC() // clean up garbage from init
+ runtime.ReadMemStats(&memstats) // first call can do some allocations
+ runtime.MemProfileRate = 0 // disable profiler
+ stacks := memstats.Alloc // ignore stacks
flag.Parse()
for i := 0; i < 1<<7; i++ {
for j := 1; j <= 1<<22; j <<= 1 {
if i == 0 && *chatty {
println("First alloc:", j)
}
- if a := runtime.MemStats.Alloc; a != 0 {
+ if a := memstats.Alloc - stacks; a != 0 {
println("no allocations but stats report", a, "bytes allocated")
panic("fail")
}
b := runtime.Alloc(uintptr(j))
- runtime.UpdateMemStats()
- during := runtime.MemStats.Alloc
+ runtime.ReadMemStats(&memstats)
+ during := memstats.Alloc - stacks
runtime.Free(b)
- runtime.UpdateMemStats()
- if a := runtime.MemStats.Alloc; a != 0 {
+ runtime.ReadMemStats(&memstats)
+ if a := memstats.Alloc - stacks; a != 0 {
println("allocated ", j, ": wrong stats: during=", during, " after=", a, " (want 0)")
panic("fail")
}
diff --git a/test/mallocrep1.go b/test/mallocrep1.go
index 0b1479900..f9d7286ef 100644
--- a/test/mallocrep1.go
+++ b/test/mallocrep1.go
@@ -20,7 +20,7 @@ var reverse = flag.Bool("r", false, "reverse")
var longtest = flag.Bool("l", false, "long test")
var b []*byte
-var stats = &runtime.MemStats
+var stats = new(runtime.MemStats)
func OkAmount(size, n uintptr) bool {
if n < size {
@@ -42,7 +42,7 @@ func AllocAndFree(size, count int) {
if *chatty {
fmt.Printf("size=%d count=%d ...\n", size, count)
}
- runtime.UpdateMemStats()
+ runtime.ReadMemStats(stats)
n1 := stats.Alloc
for i := 0; i < count; i++ {
b[i] = runtime.Alloc(uintptr(size))
@@ -51,13 +51,13 @@ func AllocAndFree(size, count int) {
println("lookup failed: got", base, n, "for", b[i])
panic("fail")
}
- runtime.UpdateMemStats()
+ runtime.ReadMemStats(stats)
if stats.Sys > 1e9 {
println("too much memory allocated")
panic("fail")
}
}
- runtime.UpdateMemStats()
+ runtime.ReadMemStats(stats)
n2 := stats.Alloc
if *chatty {
fmt.Printf("size=%d count=%d stats=%+v\n", size, count, *stats)
@@ -75,17 +75,17 @@ func AllocAndFree(size, count int) {
panic("fail")
}
runtime.Free(b[i])
- runtime.UpdateMemStats()
+ runtime.ReadMemStats(stats)
if stats.Alloc != uint64(alloc-n) {
println("free alloc got", stats.Alloc, "expected", alloc-n, "after free of", n)
panic("fail")
}
- if runtime.MemStats.Sys > 1e9 {
+ if stats.Sys > 1e9 {
println("too much memory allocated")
panic("fail")
}
}
- runtime.UpdateMemStats()
+ runtime.ReadMemStats(stats)
n4 := stats.Alloc
if *chatty {