--- /dev/null
+// Copyright 2011 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.
+
+// This test applies gofmt to all Go files under -root.
+// To test specific files provide a list of comma-separated
+// filenames via the -files flag: go test -files=gofmt.go .
+
+package main
+
+import (
+ "bytes"
+ "flag"
+ "fmt"
+ "go/ast"
+ "go/printer"
+ "io"
+ "os"
+ "path/filepath"
+ "runtime"
+ "strings"
+ "testing"
+)
+
+var (
+ root = flag.String("root", runtime.GOROOT(), "test root directory")
+ files = flag.String("files", "", "comma-separated list of files to test")
+ ngo = flag.Int("n", runtime.NumCPU(), "number of goroutines used")
+ verbose = flag.Bool("verbose", false, "verbose mode")
+ nfiles int // number of files processed
+)
+
+func gofmt(filename string, src *bytes.Buffer) error {
+ f, _, err := parse(filename, src.Bytes(), false)
+ if err != nil {
+ return err
+ }
+ ast.SortImports(fset, f)
+ src.Reset()
+ return (&printer.Config{printerMode, *tabWidth}).Fprint(src, fset, f)
+}
+
+func testFile(t *testing.T, b1, b2 *bytes.Buffer, filename string) {
+ // open file
+ f, err := os.Open(filename)
+ if err != nil {
+ t.Error(err)
+ return
+ }
+
+ // read file
+ b1.Reset()
+ _, err = io.Copy(b1, f)
+ f.Close()
+ if err != nil {
+ t.Error(err)
+ return
+ }
+
+ // exclude files w/ syntax errors (typically test cases)
+ if _, _, err = parse(filename, b1.Bytes(), false); err != nil {
+ if *verbose {
+ fmt.Fprintf(os.Stderr, "ignoring %s\n", err)
+ }
+ return
+ }
+
+ // gofmt file
+ if err = gofmt(filename, b1); err != nil {
+ t.Errorf("1st gofmt failed: %v", err)
+ return
+ }
+
+ // make a copy of the result
+ b2.Reset()
+ b2.Write(b1.Bytes())
+
+ // gofmt result again
+ if err = gofmt(filename, b2); err != nil {
+ t.Errorf("2nd gofmt failed: %v", err)
+ return
+ }
+
+ // the first and 2nd result should be identical
+ if bytes.Compare(b1.Bytes(), b2.Bytes()) != 0 {
+ t.Errorf("%s: not idempotent", filename)
+ }
+}
+
+func testFiles(t *testing.T, filenames <-chan string, done chan<- int) {
+ b1 := new(bytes.Buffer)
+ b2 := new(bytes.Buffer)
+ for filename := range filenames {
+ testFile(t, b1, b2, filename)
+ }
+ done <- 0
+}
+
+func genFilenames(t *testing.T, filenames chan<- string) {
+ defer close(filenames)
+
+ handleFile := func(filename string, fi os.FileInfo, err error) error {
+ if err != nil {
+ t.Error(err)
+ return nil
+ }
+ if isGoFile(fi) {
+ filenames <- filename
+ nfiles++
+ }
+ return nil
+ }
+
+ // test Go files provided via -files, if any
+ if *files != "" {
+ for _, filename := range strings.Split(*files, ",") {
+ fi, err := os.Stat(filename)
+ handleFile(filename, fi, err)
+ }
+ return // ignore files under -root
+ }
+
+ // otherwise, test all Go files under *root
+ filepath.Walk(*root, handleFile)
+}
+
+func TestAll(t *testing.T) {
+ if testing.Short() {
+ return
+ }
+
+ if *ngo < 1 {
+ *ngo = 1 // make sure test is run
+ }
+ if *verbose {
+ fmt.Printf("running test using %d goroutines\n", *ngo)
+ }
+
+ // generate filenames
+ filenames := make(chan string, 32)
+ go genFilenames(t, filenames)
+
+ // launch test goroutines
+ done := make(chan int)
+ for i := 0; i < *ngo; i++ {
+ go testFiles(t, filenames, done)
+ }
+
+ // wait for all test goroutines to complete
+ for i := 0; i < *ngo; i++ {
+ <-done
+ }
+
+ if *verbose {
+ fmt.Printf("processed %d files\n", nfiles)
+ }
+}
+++ /dev/null
-#!/usr/bin/env bash
-# Copyright 2009 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.
-
-eval $(go tool make --no-print-directory -f ../../Make.inc go-env)
-if [ -z "$O" ]; then
- echo 'missing $O - maybe no Make.$GOARCH?' 1>&2
- exit 1
-fi
-
-CMD="./gofmt"
-TMP1=test_tmp1.go
-TMP2=test_tmp2.go
-TMP3=test_tmp3.go
-COUNT=0
-rm -f _failed
-
-count() {
- #echo $1
- let COUNT=$COUNT+1
- let M=$COUNT%10
- if [ $M == 0 ]; then
- echo -n "."
- fi
-}
-
-
-error() {
- echo $1
- touch _failed
-}
-
-# apply to one file
-apply1() {
- # the following files are skipped because they are test cases
- # for syntax errors and thus won't parse in the first place:
- case `basename "$F"` in
- func3.go | const2.go | char_lit1.go | blank1.go | ddd1.go | \
- bug014.go | bug050.go | bug068.go | bug083.go | bug088.go | \
- bug106.go | bug121.go | bug125.go | bug133.go | bug160.go | \
- bug163.go | bug166.go | bug169.go | bug217.go | bug222.go | \
- bug226.go | bug228.go | bug248.go | bug274.go | bug280.go | \
- bug282.go | bug287.go | bug298.go | bug299.go | bug300.go | \
- bug302.go | bug306.go | bug322.go | bug324.go | bug335.go | \
- bug340.go | bug349.go | bug351.go | bug358.go | bug367.go | \
- bug388.go | bug394.go ) return ;;
- esac
- # the following directories are skipped because they contain test
- # cases for syntax errors and thus won't parse in the first place:
- case `dirname "$F"` in
- $GOROOT/test/syntax ) return ;;
- esac
- #echo $1 $2
- "$1" "$2"; count "$F"
-}
-
-
-# apply to local files
-applydot() {
- for F in `find . -name "*.go" | grep -v "._"`; do
- apply1 "$1" $F
- done
-}
-
-
-# apply to all .go files we can find
-apply() {
- for F in `find "$GOROOT" -name "*.go" | grep -v "._"`; do
- apply1 "$1" $F
- done
-}
-
-
-cleanup() {
- rm -f $TMP1 $TMP2 $TMP3
-}
-
-
-silent() {
- cleanup
- $CMD "$1" > /dev/null 2> $TMP1
- if [ $? != 0 ]; then
- cat $TMP1
- error "Error (silent mode test): test.sh $1"
- fi
-}
-
-
-idempotent() {
- cleanup
- $CMD "$1" > $TMP1
- if [ $? != 0 ]; then
- error "Error (step 1 of idempotency test): test.sh $1"
- fi
-
- $CMD $TMP1 > $TMP2
- if [ $? != 0 ]; then
- error "Error (step 2 of idempotency test): test.sh $1"
- fi
-
- $CMD $TMP2 > $TMP3
- if [ $? != 0 ]; then
- error "Error (step 3 of idempotency test): test.sh $1"
- fi
-
- cmp -s $TMP2 $TMP3
- if [ $? != 0 ]; then
- diff $TMP2 $TMP3
- error "Error (step 4 of idempotency test): test.sh $1"
- fi
-}
-
-
-valid() {
- cleanup
- $CMD "$1" > $TMP1
- if [ $? != 0 ]; then
- error "Error (step 1 of validity test): test.sh $1"
- fi
-
- $GC -o /dev/null $TMP1
- if [ $? != 0 ]; then
- error "Error (step 2 of validity test): test.sh $1"
- fi
-}
-
-
-runtest() {
- #echo "Testing silent mode"
- cleanup
- "$1" silent "$2"
-
- #echo "Testing idempotency"
- cleanup
- "$1" idempotent "$2"
-}
-
-
-runtests() {
- if [ $# = 0 ]; then
- runtest apply
- # verify the pretty-printed files can be compiled with $GC again
- # do it in local directory only because of the prerequisites required
- #echo "Testing validity"
- # Disabled for now due to dependency problems
- # cleanup
- # applydot valid
- else
- for F in "$@"; do
- runtest apply1 "$F"
- done
- fi
-}
-
-
-# run over all .go files
-runtests "$@"
-cleanup
-
-if [ -f _failed ]; then
- rm _failed
- exit 1
-fi
-
-# done
-echo
-echo "PASSED ($COUNT tests)"