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

//go:build go1.18
// +build go1.18

package vulncheck

import (
	"context"
	"io"
	"runtime"
	"strings"

	"golang.org/x/tools/go/packages"
	"golang.org/x/vuln/internal/derrors"
	"golang.org/x/vuln/vulncheck/internal/binscan"
)

// Binary detects presence of vulnerable symbols in exe. The
// imports, require, and call graph are all unavailable (nil).
func Binary(ctx context.Context, exe io.ReaderAt, cfg *Config) (_ *Result, err error) {
	defer derrors.Wrap(&err, "vulncheck.Binary")

	mods, packageSymbols, err := binscan.ExtractPackagesAndSymbols(exe)
	if err != nil {
		return nil, err
	}
	cmods := convertModules(mods)
	modVulns, err := fetchVulnerabilities(ctx, cfg.Client, cmods)
	if err != nil {
		return nil, err
	}
	modVulns = modVulns.filter(lookupEnv("GOOS", runtime.GOOS), lookupEnv("GOARCH", runtime.GOARCH))
	result := &Result{}
	for pkg, symbols := range packageSymbols {
		mod := findPackageModule(pkg, cmods)
		if cfg.ImportsOnly {
			addImportsOnlyVulns(pkg, mod, symbols, result, modVulns)
		} else {
			addSymbolVulns(pkg, mod, symbols, result, modVulns)
		}
	}
	setModules(result, cmods)
	return result, nil
}

// addImportsOnlyVulns adds Vuln entries to result in imports only mode, i.e., for each vulnerable symbol
// of pkg.
func addImportsOnlyVulns(pkg, mod string, symbols []string, result *Result, modVulns moduleVulnerabilities) {
	for _, osv := range modVulns.vulnsForPackage(pkg) {
		for _, affected := range osv.Affected {
			if affected.Package.Name != pkg {
				continue
			}

			var syms []string
			if len(affected.EcosystemSpecific.Symbols) == 0 {
				// If every symbol of pkg is vulnerable, we would ideally compute
				// every symbol mentioned in the pkg and then add Vuln entry for it,
				// just as we do in Source. However, we don't have code of pkg here
				// so we have to do best we can, which is the symbols of pkg actually
				// appearing in the binary.
				syms = symbols
			} else {
				syms = affected.EcosystemSpecific.Symbols
			}

			for _, symbol := range syms {
				vuln := &Vuln{
					OSV:     osv,
					Symbol:  symbol,
					PkgPath: pkg,
					ModPath: mod,
				}
				result.Vulns = append(result.Vulns, vuln)
			}
		}
	}
}

// addSymbolVulns adds Vuln entries to result for every symbol of pkg in the binary that is vulnerable.
func addSymbolVulns(pkg, mod string, symbols []string, result *Result, modVulns moduleVulnerabilities) {
	for _, symbol := range symbols {
		for _, osv := range modVulns.vulnsForSymbol(pkg, symbol) {
			for _, affected := range osv.Affected {
				if affected.Package.Name != pkg {
					continue
				}
				vuln := &Vuln{
					OSV:     osv,
					Symbol:  symbol,
					PkgPath: pkg,
					ModPath: mod,
				}
				result.Vulns = append(result.Vulns, vuln)
				break
			}
		}
	}
}

func convertModules(mods []*packages.Module) []*Module {
	vmods := make([]*Module, len(mods))
	convertMod := newModuleConverter()
	for i, mod := range mods {
		vmods[i] = convertMod(mod)
	}
	return vmods
}

// findPackageModule returns the path of a module that could contain the import
// path pkg. It uses paths only. It is possible but unlikely for a package path
// to match two or more different module paths. We just take the first one.
// If no module path matches, findPackageModule returns the empty string.
func findPackageModule(pkg string, mods []*Module) string {
	for _, m := range mods {
		if pkg == m.Path || strings.HasPrefix(pkg, m.Path+"/") {
			return m.Path
		}
	}
	return ""
}
