From f04d5836181dec3ec1b7e427607f02fa7a204a2d Mon Sep 17 00:00:00 2001 From: Dmitry Vyukov Date: Mon, 5 Jun 2017 10:37:37 +0200 Subject: testing: parallelize tests over count Currently all package tests are executed once with Parallel tests executed in parallel. Then this process is repeated count*cpu times. Tests are not parallelized over count*cpu. Parallelizing over cpu is not possible as GOMAXPROCS is a global setting. But it is possible for count. Parallelize over count. Brings down testing of my package with -count=100 form 10s to 0.3s. Change-Id: I76d8322adeb8c5c6e70b99af690291fd69d6402a Reviewed-on: https://go-review.googlesource.com/44830 Run-TryBot: Dmitry Vyukov TryBot-Result: Gobot Gobot Reviewed-by: Ian Lance Taylor --- src/testing/testing.go | 50 ++++++++++++++++++++++++-------------------------- 1 file changed, 24 insertions(+), 26 deletions(-) (limited to 'src/testing/testing.go') diff --git a/src/testing/testing.go b/src/testing/testing.go index 579a30ca1e..9e519f5cb9 100644 --- a/src/testing/testing.go +++ b/src/testing/testing.go @@ -991,27 +991,29 @@ func runTests(matchString func(pat, str string) (bool, error), tests []InternalT ok = true for _, procs := range cpuList { runtime.GOMAXPROCS(procs) - ctx := newTestContext(*parallel, newMatcher(matchString, *match, "-test.run")) - t := &T{ - common: common{ - signal: make(chan bool), - barrier: make(chan bool), - w: os.Stdout, - chatty: *chatty, - }, - context: ctx, - } - tRunner(t, func(t *T) { - for _, test := range tests { - t.Run(test.Name, test.F) + for i := uint(0); i < *count; i++ { + ctx := newTestContext(*parallel, newMatcher(matchString, *match, "-test.run")) + t := &T{ + common: common{ + signal: make(chan bool), + barrier: make(chan bool), + w: os.Stdout, + chatty: *chatty, + }, + context: ctx, } - // Run catching the signal rather than the tRunner as a separate - // goroutine to avoid adding a goroutine during the sequential - // phase as this pollutes the stacktrace output when aborting. - go func() { <-t.signal }() - }) - ok = ok && !t.Failed() - ran = ran || t.ran + tRunner(t, func(t *T) { + for _, test := range tests { + t.Run(test.Name, test.F) + } + // Run catching the signal rather than the tRunner as a separate + // goroutine to avoid adding a goroutine during the sequential + // phase as this pollutes the stacktrace output when aborting. + go func() { <-t.signal }() + }) + ok = ok && !t.Failed() + ran = ran || t.ran + } } return ran, ok } @@ -1167,13 +1169,9 @@ func parseCpuList() { fmt.Fprintf(os.Stderr, "testing: invalid value %q for -test.cpu\n", val) os.Exit(1) } - for i := uint(0); i < *count; i++ { - cpuList = append(cpuList, cpu) - } + cpuList = append(cpuList, cpu) } if cpuList == nil { - for i := uint(0); i < *count; i++ { - cpuList = append(cpuList, runtime.GOMAXPROCS(-1)) - } + cpuList = append(cpuList, runtime.GOMAXPROCS(-1)) } } -- cgit v1.3