From: Michael Matloob Date: Thu, 4 Dec 2025 19:21:44 +0000 (-0500) Subject: cmd/internal/fuzztest: move fuzz tests out of cmd/go test suite X-Git-Tag: go1.26rc1~2^2~16 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=a753a9ed54c7ead93e56e5b183b743877b7695a6;p=gostls13.git cmd/internal/fuzztest: move fuzz tests out of cmd/go test suite They are very slow: taking them out of the cmd/go test suite makes the go command tests go from about 80 seconds to run on my system, to about 50 seconds to run. Change-Id: I19b5c252bd2b6e6d64821cada961ddaa6a6a6964 Reviewed-on: https://go-review.googlesource.com/c/go/+/726960 Auto-Submit: Michael Matloob Reviewed-by: Alan Donovan Reviewed-by: Michael Matloob LUCI-TryBot-Result: Go LUCI --- diff --git a/src/cmd/go/internal/test/test.go b/src/cmd/go/internal/test/test.go index b30b2abc0e..ddc9c81baf 100644 --- a/src/cmd/go/internal/test/test.go +++ b/src/cmd/go/internal/test/test.go @@ -736,7 +736,7 @@ func runTest(ctx context.Context, cmd *base.Command, args []string) { // Otherwise, if fuzzing identifies a failure it could corrupt checksums in // the module cache (or permanently alter the behavior of std tests for all // users) by writing the failing input to the package's testdata directory. - // (See https://golang.org/issue/48495 and test_fuzz_modcache.txt.) + // (See https://golang.org/issue/48495 and cmd/internal/fuzztest/test_fuzz_modcache.txt.) mainMods := moduleLoaderState.MainModules if m := pkgs[0].Module; m != nil && m.Path != "" { if !mainMods.Contains(m.Path) { diff --git a/src/cmd/internal/fuzztest/script_test.go b/src/cmd/internal/fuzztest/script_test.go new file mode 100644 index 0000000000..e8fe701e17 --- /dev/null +++ b/src/cmd/internal/fuzztest/script_test.go @@ -0,0 +1,22 @@ +// Copyright 2025 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package fuzztest + +import ( + "cmd/internal/script/scripttest" + "flag" + "internal/testenv" + "testing" +) + +//go:generate go test cmd/internal/fuzztest -v -run=TestScript/README --fixreadme + +var fixReadme = flag.Bool("fixreadme", false, "if true, update README for script tests") + +func TestScript(t *testing.T) { + testenv.MustHaveGoBuild(t) + testenv.SkipIfShortAndSlow(t) + scripttest.RunToolScriptTest(t, nil, "testdata/script", *fixReadme) +} diff --git a/src/cmd/internal/fuzztest/testdata/script/README b/src/cmd/internal/fuzztest/testdata/script/README new file mode 100644 index 0000000000..9ec997a138 --- /dev/null +++ b/src/cmd/internal/fuzztest/testdata/script/README @@ -0,0 +1,286 @@ +This file is generated by 'go generate'. DO NOT EDIT. + +This directory holds test scripts *.txt run during 'go test cmd/'. +To run a specific script foo.txt + + go test cmd/ -run=Script/^foo$ + +In general script files should have short names: a few words, + not whole sentences. +The first word should be the general category of behavior being tested, +often the name of a go subcommand (build, link, compile, ...) or concept (vendor, pattern). + +Each script is a text archive (go doc internal/txtar). +The script begins with an actual command script to run +followed by the content of zero or more supporting files to +create in the script's temporary file system before it starts executing. + +As an example, run_hello.txt says: + + # hello world + go run hello.go + stderr 'hello world' + ! stdout . + + -- hello.go -- + package main + func main() { println("hello world") } + +Each script runs in a fresh temporary work directory tree, available to scripts as $WORK. +Scripts also have access to other environment variables, including: + + GOARCH= + GOOS= + TMPDIR=$WORK/tmp + devnull= + goversion= + +On Plan 9, the variables $path and $home are set instead of $PATH and $HOME. +On Windows, the variables $USERPROFILE and $TMP are set instead of +$HOME and $TMPDIR. + +The lines at the top of the script are a sequence of commands to be executed by +a small script engine configured in .../cmd/internal/script/scripttest/run.go (not the system shell). + +Each line of a script is parsed into a sequence of space-separated command +words, with environment variable expansion within each word and # marking +an end-of-line comment. Additional variables named ':' and '/' are expanded +within script arguments (expanding to the value of os.PathListSeparator and +os.PathSeparator respectively) but are not inherited in subprocess environments. + +Adding single quotes around text keeps spaces in that text from being treated +as word separators and also disables environment variable expansion. Inside a +single-quoted block of text, a repeated single quote indicates a literal single +quote, as in: + + 'Don''t communicate by sharing memory.' + +A line beginning with # is a comment and conventionally explains what is being +done or tested at the start of a new section of the script. + +Commands are executed one at a time, and errors are checked for each command; +if any command fails unexpectedly, no subsequent commands in the script are +executed. The command prefix ! indicates that the command on the rest of the +line (typically go or a matching predicate) must fail instead of succeeding. +The command prefix ? indicates that the command may or may not succeed, but the +script should continue regardless. + +The command prefix [cond] indicates that the command on the rest of the line +should only run when the condition is satisfied. + +A condition can be negated: [!root] means to run the rest of the line only if +the user is not root. Multiple conditions may be given for a single command, +for example, '[linux] [amd64] skip'. The command will run if all conditions are +satisfied. + +When TestScript runs a script and the script fails, by default TestScript shows +the execution of the most recent phase of the script (since the last # comment) +and only shows the # comments for earlier phases. + +Note also that in reported output, the actual name of the per-script temporary directory +has been consistently replaced with the literal string $WORK. + +The available commands are: +cat files... + concatenate files and print to the script's stdout buffer + + +cc args... + run the platform C compiler + + +cd dir + change the working directory + + +chmod perm paths... + change file mode bits + + Changes the permissions of the named files or directories to + be equal to perm. + Only numerical permissions are supported. + +cmp [-q] file1 file2 + compare files for differences + + By convention, file1 is the actual data and file2 is the + expected data. + The command succeeds if the file contents are identical. + File1 can be 'stdout' or 'stderr' to compare the stdout or + stderr buffer from the most recent command. + +cmpenv [-q] file1 file2 + compare files for differences, with environment expansion + + By convention, file1 is the actual data and file2 is the + expected data. + The command succeeds if the file contents are identical + after substituting variables from the script environment. + File1 can be 'stdout' or 'stderr' to compare the script's + stdout or stderr buffer. + +cp src... dst + copy files to a target file or directory + + src can include 'stdout' or 'stderr' to copy from the + script's stdout or stderr buffer. + +echo string... + display a line of text + + +env [key[=value]...] + set or log the values of environment variables + + With no arguments, print the script environment to the log. + Otherwise, add the listed key=value pairs to the environment + or print the listed keys. + +exec program [args...] [&] + run an executable program with arguments + + Note that 'exec' does not terminate the script (unlike Unix + shells). + +exists [-readonly] [-exec] file... + check that files exist + + +go [args...] [&] + run the 'go' program provided by the script host + + +grep [-count=N] [-q] 'pattern' file + find lines in a file that match a pattern + + The command succeeds if at least one match (or the exact + count, if given) is found. + The -q flag suppresses printing of matches. + +help [-v] name... + log help text for commands and conditions + + To display help for a specific condition, enclose it in + brackets: 'help [amd64]'. + To display complete documentation when listing all commands, + pass the -v flag. + +mkdir path... + create directories, if they do not already exist + + Unlike Unix mkdir, parent directories are always created if + needed. + +mv old new + rename a file or directory to a new path + + OS-specific restrictions may apply when old and new are in + different directories. + +replace [old new]... file + replace strings in a file + + The 'old' and 'new' arguments are unquoted as if in quoted + Go strings. + +rm path... + remove a file or directory + + If the path is a directory, its contents are removed + recursively. + +skip [msg] + skip the current test + + +sleep duration [&] + sleep for a specified duration + + The duration must be given as a Go time.Duration string. + +stderr [-count=N] [-q] 'pattern' file + find lines in the stderr buffer that match a pattern + + The command succeeds if at least one match (or the exact + count, if given) is found. + The -q flag suppresses printing of matches. + +stdout [-count=N] [-q] 'pattern' file + find lines in the stdout buffer that match a pattern + + The command succeeds if at least one match (or the exact + count, if given) is found. + The -q flag suppresses printing of matches. + +stop [msg] + stop execution of the script + + The message is written to the script log, but no error is + reported from the script engine. + +symlink path -> target + create a symlink + + Creates path as a symlink to target. + The '->' token (like in 'ls -l' output on Unix) is required. + +wait + wait for completion of background commands + + Waits for all background commands to complete. + The output (and any error) from each command is printed to + the log in the order in which the commands were started. + After the call to 'wait', the script's stdout and stderr + buffers contain the concatenation of the background + commands' outputs. + + + +The available conditions are: +[GOARCH:*] + runtime.GOARCH == +[GODEBUG:*] + GODEBUG contains +[GOEXPERIMENT:*] + GOEXPERIMENT is enabled +[GOOS:*] + runtime.GOOS == +[asan] + GOOS/GOARCH supports -asan +[buildmode:*] + go supports -buildmode= +[cgo] + host CGO_ENABLED +[cgolinkext] + platform requires external linking for cgo +[compiler:*] + runtime.Compiler == +[cross] + cmd/go GOOS/GOARCH != GOHOSTOS/GOHOSTARCH +[exec:*] + names an executable in the test binary's PATH +[fuzz] + GOOS/GOARCH supports -fuzz +[fuzz-instrumented] + GOOS/GOARCH supports -fuzz with instrumentation +[go-builder] + GO_BUILDER_NAME is non-empty +[link] + testenv.HasLink() +[msan] + GOOS/GOARCH supports -msan +[mustlinkext] + platform always requires external linking +[pielinkext] + platform requires external linking for PIE +[race] + GOOS/GOARCH supports -race +[root] + os.Geteuid() == 0 +[short] + testing.Short() +[symlink] + testenv.HasSymlink() +[verbose] + testing.Verbose() + diff --git a/src/cmd/go/testdata/script/test_fuzz.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_cache.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_cache.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_cache.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_cache.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_cgo.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_cgo.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_cgo.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_cgo.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_chatty.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_chatty.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_chatty.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_chatty.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_cleanup.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_cleanup.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_cleanup.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_cleanup.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_context.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_context.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_context.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_context.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_cov.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_cov.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_cov.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_cov.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_deadline.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_deadline.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_deadline.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_deadline.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_dup_cache.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_dup_cache.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_dup_cache.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_dup_cache.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_err_deadlock.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_err_deadlock.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_err_deadlock.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_err_deadlock.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_fuzztime.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_fuzztime.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_fuzztime.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_fuzztime.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_io_error.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_io_error.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_io_error.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_io_error.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_limit_dup_entry.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_limit_dup_entry.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_limit_dup_entry.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_limit_dup_entry.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_match.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_match.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_match.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_match.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_minimize.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_minimize.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_minimize.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_minimize.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_minimize_dirty_cov.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_minimize_dirty_cov.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_minimize_dirty_cov.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_minimize_dirty_cov.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_minimize_interesting.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_minimize_interesting.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_minimize_interesting.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_minimize_interesting.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_multiple.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_multiple.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_multiple.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_multiple.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_mutate_crash.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutate_crash.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_mutate_crash.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutate_crash.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_mutate_fail.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutate_fail.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_mutate_fail.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutate_fail.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_mutator.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutator.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_mutator.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutator.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_mutator_repeat.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutator_repeat.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_mutator_repeat.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_mutator_repeat.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_non_crash_signal.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_non_crash_signal.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_non_crash_signal.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_non_crash_signal.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_parallel.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_parallel.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_parallel.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_parallel.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_profile_flags.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_profile_flags.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_profile_flags.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_profile_flags.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_return.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_return.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_return.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_return.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_run.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_run.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_run.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_run.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_seed_corpus.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_seed_corpus.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_seed_corpus.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_seed_corpus.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_setenv.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_setenv.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_setenv.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_setenv.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_test_race.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_test_race.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_test_race.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_test_race.txt diff --git a/src/cmd/go/testdata/script/test_fuzz_unsupported.txt b/src/cmd/internal/fuzztest/testdata/script/test_fuzz_unsupported.txt similarity index 100% rename from src/cmd/go/testdata/script/test_fuzz_unsupported.txt rename to src/cmd/internal/fuzztest/testdata/script/test_fuzz_unsupported.txt diff --git a/src/cmd/internal/script/scripttest/run.go b/src/cmd/internal/script/scripttest/run.go index 8dff13e22e..2a909f656d 100644 --- a/src/cmd/internal/script/scripttest/run.go +++ b/src/cmd/internal/script/scripttest/run.go @@ -137,6 +137,9 @@ func RunToolScriptTest(t *testing.T, repls []ToolReplacement, scriptsdir string, env := os.Environ() prependToPath(env, filepath.Join(tgr, "bin")) env = setenv(env, "GOROOT", tgr) + // GOOS and GOARCH are expected to be set by the toolchain script conditions. + env = setenv(env, "GOOS", runtime.GOOS) + env = setenv(env, "GOARCH", runtime.GOARCH) for _, repl := range repls { // consistency check chunks := strings.Split(repl.EnvVar, "=")