// Copyright 2014 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 main

import (
	"bufio"
	"bytes"
	"fmt"
	"internal/testenv"
	"io/ioutil"
	"os"
	"os/exec"
	"path/filepath"
	"runtime"
	"strings"
	"testing"
	"text/template"
)

var testnmpath string // path to nm command created for testing purposes

// The TestMain function creates a nm command for testing purposes and
// deletes it after the tests have been run.
func TestMain(m *testing.M) {
	os.Exit(testMain(m))
}

func testMain(m *testing.M) int {
	if !testenv.HasGoBuild() {
		return 0
	}

	tmpDir, err := ioutil.TempDir("", "TestNM")
	if err != nil {
		fmt.Println("TempDir failed:", err)
		return 2
	}
	defer os.RemoveAll(tmpDir)

	testnmpath = filepath.Join(tmpDir, "testnm.exe")
	gotool, err := testenv.GoTool()
	if err != nil {
		fmt.Println("GoTool failed:", err)
		return 2
	}
	out, err := exec.Command(gotool, "build", "-o", testnmpath, "cmd/nm").CombinedOutput()
	if err != nil {
		fmt.Printf("go build -o %v cmd/nm: %v\n%s", testnmpath, err, string(out))
		return 2
	}

	return m.Run()
}

func TestNonGoExecs(t *testing.T) {
	testfiles := []string{
		"elf/testdata/gcc-386-freebsd-exec",
		"elf/testdata/gcc-amd64-linux-exec",
		"macho/testdata/gcc-386-darwin-exec",
		"macho/testdata/gcc-amd64-darwin-exec",
		// "pe/testdata/gcc-amd64-mingw-exec", // no symbols!
		"pe/testdata/gcc-386-mingw-exec",
		"plan9obj/testdata/amd64-plan9-exec",
		"plan9obj/testdata/386-plan9-exec",
	}
	for _, f := range testfiles {
		exepath := filepath.Join(runtime.GOROOT(), "src", "debug", f)
		cmd := exec.Command(testnmpath, exepath)
		out, err := cmd.CombinedOutput()
		if err != nil {
			t.Errorf("go tool nm %v: %v\n%s", exepath, err, string(out))
		}
	}
}

func testGoExec(t *testing.T, iscgo, isexternallinker bool) {
	tmpdir, err := ioutil.TempDir("", "TestGoExec")
	if err != nil {
		t.Fatal(err)
	}
	defer os.RemoveAll(tmpdir)

	src := filepath.Join(tmpdir, "a.go")
	file, err := os.Create(src)
	if err != nil {
		t.Fatal(err)
	}
	err = template.Must(template.New("main").Parse(testexec)).Execute(file, iscgo)
	if e := file.Close(); err == nil {
		err = e
	}
	if err != nil {
		t.Fatal(err)
	}

	exe := filepath.Join(tmpdir, "a.exe")
	args := []string{"build", "-o", exe}
	if iscgo {
		linkmode := "internal"
		if isexternallinker {
			linkmode = "external"
		}
		args = append(args, "-ldflags", "-linkmode="+linkmode)
	}
	args = append(args, src)
	out, err := exec.Command(testenv.GoToolPath(t), args...).CombinedOutput()
	if err != nil {
		t.Fatalf("building test executable failed: %s %s", err, out)
	}

	out, err = exec.Command(exe).CombinedOutput()
	if err != nil {
		t.Fatalf("running test executable failed: %s %s", err, out)
	}
	names := make(map[string]string)
	for _, line := range strings.Split(string(out), "\n") {
		if line == "" {
			continue
		}
		f := strings.Split(line, "=")
		if len(f) != 2 {
			t.Fatalf("unexpected output line: %q", line)
		}
		names["main."+f[0]] = f[1]
	}

	runtimeSyms := map[string]string{
		"runtime.text":      "T",
		"runtime.etext":     "T",
		"runtime.rodata":    "R",
		"runtime.erodata":   "R",
		"runtime.epclntab":  "R",
		"runtime.noptrdata": "D",
	}

	out, err = exec.Command(testnmpath, exe).CombinedOutput()
	if err != nil {
		t.Fatalf("go tool nm: %v\n%s", err, string(out))
	}
	scanner := bufio.NewScanner(bytes.NewBuffer(out))
	dups := make(map[string]bool)
	for scanner.Scan() {
		f := strings.Fields(scanner.Text())
		if len(f) < 3 {
			continue
		}
		name := f[2]
		if addr, found := names[name]; found {
			if want, have := addr, "0x"+f[0]; have != want {
				t.Errorf("want %s address for %s symbol, but have %s", want, name, have)
			}
			delete(names, name)
		}
		if _, found := dups[name]; found {
			t.Errorf("duplicate name of %q is found", name)
		}
		if stype, found := runtimeSyms[name]; found {
			if runtime.GOOS == "plan9" && stype == "R" {
				// no read-only data segment symbol on Plan 9
				stype = "D"
			}
			if want, have := stype, strings.ToUpper(f[1]); have != want {
				t.Errorf("want %s type for %s symbol, but have %s", want, name, have)
			}
			delete(runtimeSyms, name)
		}
	}
	err = scanner.Err()
	if err != nil {
		t.Fatalf("error reading nm output: %v", err)
	}
	if len(names) > 0 {
		t.Errorf("executable is missing %v symbols", names)
	}
	if len(runtimeSyms) > 0 {
		t.Errorf("executable is missing %v symbols", runtimeSyms)
	}
}

func TestGoExec(t *testing.T) {
	testGoExec(t, false, false)
}

func testGoLib(t *testing.T, iscgo bool) {
	tmpdir, err := ioutil.TempDir("", "TestGoLib")
	if err != nil {
		t.Fatal(err)
	}
	defer os.RemoveAll(tmpdir)

	gopath := filepath.Join(tmpdir, "gopath")
	libpath := filepath.Join(gopath, "src", "mylib")

	err = os.MkdirAll(libpath, 0777)
	if err != nil {
		t.Fatal(err)
	}
	src := filepath.Join(libpath, "a.go")
	file, err := os.Create(src)
	if err != nil {
		t.Fatal(err)
	}
	err = template.Must(template.New("mylib").Parse(testlib)).Execute(file, iscgo)
	if e := file.Close(); err == nil {
		err = e
	}
	if err != nil {
		t.Fatal(err)
	}

	args := []string{"install", "mylib"}
	cmd := exec.Command(testenv.GoToolPath(t), args...)
	cmd.Env = append(os.Environ(), "GOPATH="+gopath)
	out, err := cmd.CombinedOutput()
	if err != nil {
		t.Fatalf("building test lib failed: %s %s", err, out)
	}
	pat := filepath.Join(gopath, "pkg", "*", "mylib.a")
	ms, err := filepath.Glob(pat)
	if err != nil {
		t.Fatal(err)
	}
	if len(ms) == 0 {
		t.Fatalf("cannot found paths for pattern %s", pat)
	}
	mylib := ms[0]

	out, err = exec.Command(testnmpath, mylib).CombinedOutput()
	if err != nil {
		t.Fatalf("go tool nm: %v\n%s", err, string(out))
	}
	type symType struct {
		Type  string
		Name  string
		CSym  bool
		Found bool
	}
	var syms = []symType{
		{"B", "%22%22.Testdata", false, false},
		{"T", "%22%22.Testfunc", false, false},
	}
	if iscgo {
		syms = append(syms, symType{"B", "%22%22.TestCgodata", false, false})
		syms = append(syms, symType{"T", "%22%22.TestCgofunc", false, false})
		if runtime.GOOS == "darwin" || (runtime.GOOS == "windows" && runtime.GOARCH == "386") {
			syms = append(syms, symType{"D", "_cgodata", true, false})
			syms = append(syms, symType{"T", "_cgofunc", true, false})
		} else {
			syms = append(syms, symType{"D", "cgodata", true, false})
			syms = append(syms, symType{"T", "cgofunc", true, false})
		}
	}
	scanner := bufio.NewScanner(bytes.NewBuffer(out))
	for scanner.Scan() {
		f := strings.Fields(scanner.Text())
		var typ, name string
		var csym bool
		if iscgo {
			if len(f) < 4 {
				continue
			}
			csym = !strings.Contains(f[0], "_go_.o")
			typ = f[2]
			name = f[3]
		} else {
			if len(f) < 3 {
				continue
			}
			typ = f[1]
			name = f[2]
		}
		for i := range syms {
			sym := &syms[i]
			if sym.Type == typ && sym.Name == name && sym.CSym == csym {
				if sym.Found {
					t.Fatalf("duplicate symbol %s %s", sym.Type, sym.Name)
				}
				sym.Found = true
			}
		}
	}
	err = scanner.Err()
	if err != nil {
		t.Fatalf("error reading nm output: %v", err)
	}
	for _, sym := range syms {
		if !sym.Found {
			t.Errorf("cannot found symbol %s %s", sym.Type, sym.Name)
		}
	}
}

func TestGoLib(t *testing.T) {
	testGoLib(t, false)
}

const testexec = `
package main

import "fmt"
{{if .}}import "C"
{{end}}

func main() {
	testfunc()
}

var testdata uint32

func testfunc() {
	fmt.Printf("main=%p\n", main)
	fmt.Printf("testfunc=%p\n", testfunc)
	fmt.Printf("testdata=%p\n", &testdata)
}
`

const testlib = `
package mylib

{{if .}}
// int cgodata = 5;
// void cgofunc(void) {}
import "C"

var TestCgodata = C.cgodata

func TestCgofunc() {
	C.cgofunc()
}
{{end}}

var Testdata uint32

func Testfunc() {}
`
