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

// Cgo; see gmp.go for an overview.

// TODO(rsc):
//	Emit correct line number annotations.
//	Make 6g understand the annotations.

package main

import (
	"fmt"
	"go/ast"
	"os"
	"strings"
)

func usage() { fmt.Fprint(os.Stderr, "usage: cgo [compiler options] file.go ...\n") }

var ptrSizeMap = map[string]int64{
	"386": 4,
	"amd64": 8,
	"arm": 4,
}

var expandName = map[string]string{
	"schar": "signed char",
	"uchar": "unsigned char",
	"ushort": "unsigned short",
	"uint": "unsigned int",
	"ulong": "unsigned long",
	"longlong": "long long",
	"ulonglong": "unsigned long long",
}

func main() {
	args := os.Args
	if len(args) < 2 {
		usage()
		os.Exit(2)
	}

	// Find first arg that looks like a go file and assume everything before
	// that are options to pass to gcc.
	var i int
	for i = len(args) - 1; i > 0; i-- {
		if !strings.HasSuffix(args[i], ".go") {
			break
		}
	}

	i += 1

	gccOptions, goFiles := args[1:i], args[i:]

	arch := os.Getenv("GOARCH")
	if arch == "" {
		fatal("$GOARCH is not set")
	}
	ptrSize, ok := ptrSizeMap[arch]
	if !ok {
		fatal("unknown architecture %s", arch)
	}

	// Clear locale variables so gcc emits English errors [sic].
	os.Setenv("LANG", "en_US.UTF-8")
	os.Setenv("LC_ALL", "C")
	os.Setenv("LC_CTYPE", "C")

	p := new(Prog)

	p.PtrSize = ptrSize
	p.GccOptions = gccOptions
	p.Vardef = make(map[string]*Type)
	p.Funcdef = make(map[string]*FuncType)
	p.Enumdef = make(map[string]int64)
	p.OutDefs = make(map[string]bool)

	for _, input := range goFiles {
		// Reset p.Preamble so that we don't end up with conflicting headers / defines
		p.Preamble = builtinProlog
		openProg(input, p)
		for _, cref := range p.Crefs {
			// Convert C.ulong to C.unsigned long, etc.
			if expand, ok := expandName[cref.Name]; ok {
				cref.Name = expand
			}
		}
		p.loadDebugInfo()
		for _, cref := range p.Crefs {
			switch cref.Context {
			case "call":
				if !cref.TypeName {
					// Is an actual function call.
					pos := (*cref.Expr).Pos()
					*cref.Expr = &ast.Ident{Position: pos, Value: "_C_" + cref.Name}
					p.Funcdef[cref.Name] = cref.FuncType
					break
				}
				*cref.Expr = cref.Type.Go
			case "expr":
				if cref.TypeName {
					error((*cref.Expr).Pos(), "type C.%s used as expression", cref.Name)
				}
				// If the expression refers to an enumerated value, then
				// place the identifier for the value and add it to Enumdef so
				// it will be declared as a constant in the later stage.
				if cref.Type.EnumValues != nil {
					*cref.Expr = &ast.Ident{Value: cref.Name}
					p.Enumdef[cref.Name] = cref.Type.EnumValues[cref.Name]
					break
				}
				// Reference to C variable.
				// We declare a pointer and arrange to have it filled in.
				*cref.Expr = &ast.StarExpr{X: &ast.Ident{Value: "_C_" + cref.Name}}
				p.Vardef[cref.Name] = cref.Type
			case "type":
				if !cref.TypeName {
					error((*cref.Expr).Pos(), "expression C.%s used as type", cref.Name)
				}
				*cref.Expr = cref.Type.Go
			}
		}
		if nerrors > 0 {
			os.Exit(2)
		}
		pkg := p.Package
		if dir := os.Getenv("CGOPKGPATH"); dir != "" {
			pkg = dir + "/" + pkg
		}
		p.PackagePath = pkg
		p.writeOutput(input)
	}

	p.writeDefs()
}
