// 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.

// Run "make install" to build package.

package main

import (
	"bytes"
	"go/build"
	"os"
	"path/filepath"
	"strings"
	"template"
)

// domake builds the package in dir.
// domake generates a standard Makefile and passes it
// to make on standard input.
func domake(dir, pkg string, tree *build.Tree, isCmd bool) (err os.Error) {
	makefile, err := makeMakefile(dir, pkg, tree, isCmd)
	if err != nil {
		return err
	}
	cmd := []string{"bash", "gomake", "-f-"}
	if *nuke {
		cmd = append(cmd, "nuke")
	} else if *clean {
		cmd = append(cmd, "clean")
	}
	cmd = append(cmd, "install")
	return run(dir, makefile, cmd...)
}

// makeMakefile computes the standard Makefile for the directory dir
// installing as package pkg.  It includes all *.go files in the directory
// except those in package main and those ending in _test.go.
func makeMakefile(dir, pkg string, tree *build.Tree, isCmd bool) ([]byte, os.Error) {
	if !safeName(pkg) {
		return nil, os.NewError("unsafe name: " + pkg)
	}
	targ := pkg
	targDir := tree.PkgDir()
	if isCmd {
		// use the last part of the package name for targ
		_, targ = filepath.Split(pkg)
		targDir = tree.BinDir()
	}
	dirInfo, err := build.ScanDir(dir, isCmd)
	if err != nil {
		return nil, err
	}

	cgoFiles := dirInfo.CgoFiles
	isCgo := make(map[string]bool, len(cgoFiles))
	for _, file := range cgoFiles {
		if !safeName(file) {
			return nil, os.NewError("bad name: " + file)
		}
		isCgo[file] = true
	}

	goFiles := make([]string, 0, len(dirInfo.GoFiles))
	for _, file := range dirInfo.GoFiles {
		if !safeName(file) {
			return nil, os.NewError("unsafe name: " + file)
		}
		if !isCgo[file] {
			goFiles = append(goFiles, file)
		}
	}

	oFiles := make([]string, 0, len(dirInfo.CFiles)+len(dirInfo.SFiles))
	cgoOFiles := make([]string, 0, len(dirInfo.CFiles))
	for _, file := range dirInfo.CFiles {
		if !safeName(file) {
			return nil, os.NewError("unsafe name: " + file)
		}
		// When cgo is in use, C files are compiled with gcc,
		// otherwise they're compiled with gc.
		if len(cgoFiles) > 0 {
			cgoOFiles = append(cgoOFiles, file[:len(file)-2]+".o")
		} else {
			oFiles = append(oFiles, file[:len(file)-2]+".$O")
		}
	}

	for _, file := range dirInfo.SFiles {
		if !safeName(file) {
			return nil, os.NewError("unsafe name: " + file)
		}
		oFiles = append(oFiles, file[:len(file)-2]+".$O")
	}

	var imports []string
	for _, t := range build.Path {
		imports = append(imports, t.PkgDir())
	}

	var buf bytes.Buffer
	md := makedata{targ, targDir, "pkg", goFiles, oFiles, cgoFiles, cgoOFiles, imports}
	if isCmd {
		md.Type = "cmd"
	}
	if err := makefileTemplate.Execute(&buf, &md); err != nil {
		return nil, err
	}
	return buf.Bytes(), nil
}

var safeBytes = []byte("+-./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz")

func safeName(s string) bool {
	if s == "" {
		return false
	}
	if strings.Contains(s, "..") {
		return false
	}
	for i := 0; i < len(s); i++ {
		if c := s[i]; c < 0x80 && bytes.IndexByte(safeBytes, c) < 0 {
			return false
		}
	}
	return true
}

// makedata is the data type for the makefileTemplate.
type makedata struct {
	Targ      string   // build target
	TargDir   string   // build target directory
	Type      string   // build type: "pkg" or "cmd"
	GoFiles   []string // list of non-cgo .go files
	OFiles    []string // list of .$O files
	CgoFiles  []string // list of cgo .go files
	CgoOFiles []string // list of cgo .o files, without extension
	Imports   []string // gc/ld import paths
}

var makefileTemplate = template.Must(template.New("Makefile").Parse(`
include $(GOROOT)/src/Make.inc

TARG={{.Targ}}
TARGDIR={{.TargDir}}

{{with .GoFiles}}
GOFILES=\
{{range .}}	{{.}}\
{{end}}

{{end}}
{{with .OFiles}}
OFILES=\
{{range .}}	{{.}}\
{{end}}

{{end}}
{{with .CgoFiles}}
CGOFILES=\
{{range .}}	{{.}}\
{{end}}

{{end}}
{{with .CgoOFiles}}
CGO_OFILES=\
{{range .}}	{{.}}\
{{end}}

{{end}}
GCIMPORTS={{range .Imports}}-I "{{.}}" {{end}}
LDIMPORTS={{range .Imports}}-L "{{.}}" {{end}}

include $(GOROOT)/src/Make.{{.Type}}
`))
