// Copyright (C) 2021 The Android Open Source Project
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package aidl

import (
	"android/soong/android"
	"android/soong/cc"
	"android/soong/java"
	"android/soong/rust"

	"path/filepath"
	"strings"

	"github.com/google/blueprint/proptools"
)

func addLibrary(mctx android.LoadHookContext, i *aidlInterface, version string, lang string) string {
	if lang == langJava {
		return addJavaLibrary(mctx, i, version)
	} else if lang == langRust {
		return addRustLibrary(mctx, i, version)
	}
	return addCppLibrary(mctx, i, version, lang)
}

func addCppLibrary(mctx android.LoadHookContext, i *aidlInterface, version string, lang string) string {
	cppSourceGen := i.versionedName(version) + "-" + lang + "-source"
	cppModuleGen := i.versionedName(version) + "-" + lang

	srcs, aidlRoot := i.srcsForVersion(mctx, version)
	if len(srcs) == 0 {
		// This can happen when the version is about to be frozen; the version
		// directory is created but API dump hasn't been copied there.
		// Don't create a library for the yet-to-be-frozen version.
		return ""
	}

	var overrideVndkProperties cc.VndkProperties

	if !i.isModuleForVndk(version) {
		// We only want the VNDK to include the latest interface. For interfaces in
		// development, they will be frozen, so we put their latest version in the
		// VNDK. For interfaces which are already frozen, we put their latest version
		// in the VNDK, and when that version is frozen, the version in the VNDK can
		// be updated. Otherwise, we remove this library from the VNDK, to avoid adding
		// multiple versions of the same library to the VNDK.
		overrideVndkProperties.Vndk.Enabled = proptools.BoolPtr(false)
		overrideVndkProperties.Vndk.Support_system_process = proptools.BoolPtr(false)
	}

	var commonProperties *CommonNativeBackendProperties
	if lang == langCpp {
		commonProperties = &i.properties.Backend.Cpp.CommonNativeBackendProperties
	} else if lang == langNdk || lang == langNdkPlatform {
		commonProperties = &i.properties.Backend.Ndk.CommonNativeBackendProperties
	}

	genLog := proptools.Bool(commonProperties.Gen_log)
	genTrace := proptools.Bool(i.properties.Gen_trace)

	mctx.CreateModule(aidlGenFactory, &nameProperties{
		Name: proptools.StringPtr(cppSourceGen),
	}, &aidlGenProperties{
		Srcs:                  srcs,
		AidlRoot:              aidlRoot,
		IsToT:                 version == i.nextVersion(),
		ImportsWithoutVersion: i.properties.ImportsWithoutVersion,
		Stability:             i.properties.Stability,
		Lang:                  lang,
		BaseName:              i.ModuleBase.Name(),
		GenLog:                genLog,
		Version:               i.versionForAidlGenRule(version),
		GenTrace:              genTrace,
		Unstable:              i.properties.Unstable,
		Visibility:            srcsVisibility(mctx, lang),
		Flags:                 i.flagsForAidlGenRule(version),
	})

	importExportDependencies := []string{}
	var sharedLibDependency []string
	var headerLibs []string
	var sdkVersion *string
	var minSdkVersion *string
	var stl *string
	var cpp_std *string
	var hostSupported *bool
	var addCflags []string
	targetProp := ccTargetProperties{
		// Currently necessary for host builds
		// TODO(b/31559095): bionic on host should define this
		// TODO(b/146436251): default isn't applied because the module is created
		// in PreArchMutators, when import behavior becomes explicit, the logic can
		// be moved back to LoadHook
		Host: hostProperties{Cflags: []string{
			"-D__INTRODUCED_IN(n)=",
			"-D__assert(a,b,c)=",
			// We want all the APIs to be available on the host.
			"-D__ANDROID_API__=10000"}},
		Darwin: darwinProperties{Enabled: proptools.BoolPtr(false)},
	}

	if lang == langCpp {
		importExportDependencies = append(importExportDependencies, "libbinder", "libutils")
		if genTrace {
			sharedLibDependency = append(sharedLibDependency, "libcutils")
		}
		hostSupported = i.properties.Host_supported
		minSdkVersion = i.properties.Backend.Cpp.Min_sdk_version
	} else if lang == langNdk || lang == langNdkPlatform {
		importExportDependencies = append(importExportDependencies, "libbinder_ndk")
		nonAppProps := imageProperties{
			Cflags: []string{"-DBINDER_STABILITY_SUPPORT"},
		}
		if genTrace {
			sharedLibDependency = append(sharedLibDependency, "libandroid")
			nonAppProps.Exclude_shared_libs = []string{"libandroid"}
			nonAppProps.Header_libs = []string{"libandroid_aidltrace"}
			nonAppProps.Shared_libs = []string{"libcutils"}
		}
		targetProp.Platform = nonAppProps
		targetProp.Vendor = nonAppProps
		targetProp.Product = nonAppProps
		minSdkVersion = i.properties.Backend.Ndk.Min_sdk_version
		hostSupported = i.properties.Host_supported
		if lang == langNdk && i.shouldGenerateAppNdkBackend() {
			sdkVersion = proptools.StringPtr("current")
			// Don't worry! This maps to libc++.so for the platform variant.
			stl = proptools.StringPtr("c++_shared")
		}
	} else {
		panic("Unrecognized language: " + lang)
	}

	vendorAvailable := i.properties.Vendor_available
	odmAvailable := i.properties.Odm_available
	productAvailable := i.properties.Product_available
	if lang == langCpp {
		// Vendor and product modules cannot use the libbinder (cpp) backend of AIDL in a
		// way that is stable. So, in order to prevent accidental usage of these library by
		// vendor and product forcibly disabling this version of the library.
		//
		// It may be the case in the future that we will want to enable this (if some generic
		// helper should be used by both libbinder vendor things using /dev/vndbinder as well
		// as those things using /dev/binder + libbinder_ndk to talk to stable interfaces).
		if "vintf" == proptools.String(i.properties.Stability) {
			overrideVndkProperties.Vndk.Private = proptools.BoolPtr(true)
		}
		// As libbinder is not available for the product processes, we must not create
		// product variant for the aidl_interface
		productAvailable = nil
	}

	mctx.CreateModule(aidlImplementationGeneratorFactory, &nameProperties{
		Name: proptools.StringPtr(cppModuleGen + "-generator"),
	}, &aidlImplementationGeneratorProperties{
		Lang:              lang,
		AidlInterfaceName: i.ModuleBase.Name(),
		Version:           version,
		ModuleProperties: []interface{}{
			&ccProperties{
				Name:                      proptools.StringPtr(cppModuleGen),
				Vendor_available:          vendorAvailable,
				Odm_available:             odmAvailable,
				Product_available:         productAvailable,
				Host_supported:            hostSupported,
				Defaults:                  []string{"aidl-cpp-module-defaults"},
				Double_loadable:           i.properties.Double_loadable,
				Generated_sources:         []string{cppSourceGen},
				Generated_headers:         []string{cppSourceGen},
				Export_generated_headers:  []string{cppSourceGen},
				Shared_libs:               append(importExportDependencies, sharedLibDependency...),
				Header_libs:               headerLibs,
				Export_shared_lib_headers: importExportDependencies,
				Sdk_version:               sdkVersion,
				Stl:                       stl,
				Cpp_std:                   cpp_std,
				Cflags:                    append(addCflags, "-Wextra", "-Wall", "-Werror", "-Wextra-semi"),
				Apex_available:            commonProperties.Apex_available,
				Min_sdk_version:           minSdkVersion,
				UseApexNameMacro:          true,
				Target:                    targetProp,
				Tidy:                      proptools.BoolPtr(true),
				// Do the tidy check only for the generated headers
				Tidy_flags:            []string{"--header-filter=" + android.PathForOutput(mctx).String() + ".*"},
				Tidy_checks_as_errors: []string{"*"},
			}, &i.properties.VndkProperties,
			&commonProperties.VndkProperties,
			&overrideVndkProperties,
		},
	})

	return cppModuleGen
}

func addJavaLibrary(mctx android.LoadHookContext, i *aidlInterface, version string) string {
	javaSourceGen := i.versionedName(version) + "-java-source"
	javaModuleGen := i.versionedName(version) + "-java"
	srcs, aidlRoot := i.srcsForVersion(mctx, version)
	if len(srcs) == 0 {
		// This can happen when the version is about to be frozen; the version
		// directory is created but API dump hasn't been copied there.
		// Don't create a library for the yet-to-be-frozen version.
		return ""
	}

	sdkVersion := i.properties.Backend.Java.Sdk_version
	if !proptools.Bool(i.properties.Backend.Java.Platform_apis) && sdkVersion == nil {
		// platform apis requires no default
		sdkVersion = proptools.StringPtr("system_current")
	}

	mctx.CreateModule(aidlGenFactory, &nameProperties{
		Name: proptools.StringPtr(javaSourceGen),
	}, &aidlGenProperties{
		Srcs:                  srcs,
		AidlRoot:              aidlRoot,
		IsToT:                 version == i.nextVersion(),
		ImportsWithoutVersion: i.properties.ImportsWithoutVersion,
		Stability:             i.properties.Stability,
		Lang:                  langJava,
		BaseName:              i.ModuleBase.Name(),
		Version:               i.versionForAidlGenRule(version),
		GenTrace:              proptools.Bool(i.properties.Gen_trace),
		Unstable:              i.properties.Unstable,
		Visibility:            srcsVisibility(mctx, langJava),
		Flags:                 i.flagsForAidlGenRule(version),
	})

	mctx.CreateModule(aidlImplementationGeneratorFactory, &nameProperties{
		Name: proptools.StringPtr(javaModuleGen + "-generator"),
	}, &aidlImplementationGeneratorProperties{
		Lang:              langJava,
		AidlInterfaceName: i.ModuleBase.Name(),
		Version:           version,
		ModuleProperties: []interface{}{&javaProperties{
			Name:            proptools.StringPtr(javaModuleGen),
			Installable:     proptools.BoolPtr(true),
			Defaults:        []string{"aidl-java-module-defaults"},
			Sdk_version:     sdkVersion,
			Platform_apis:   i.properties.Backend.Java.Platform_apis,
			Srcs:            []string{":" + javaSourceGen},
			Apex_available:  i.properties.Backend.Java.Apex_available,
			Min_sdk_version: i.properties.Backend.Java.Min_sdk_version,
		}},
	})

	return javaModuleGen
}

func addRustLibrary(mctx android.LoadHookContext, i *aidlInterface, version string) string {
	rustSourceGen := i.versionedName(version) + "-rust-source"
	rustModuleGen := i.versionedName(version) + "-rust"
	srcs, aidlRoot := i.srcsForVersion(mctx, version)
	if len(srcs) == 0 {
		// This can happen when the version is about to be frozen; the version
		// directory is created but API dump hasn't been copied there.
		// Don't create a library for the yet-to-be-frozen version.
		return ""
	}

	mctx.CreateModule(aidlGenFactory, &nameProperties{
		Name: proptools.StringPtr(rustSourceGen),
	}, &aidlGenProperties{
		Srcs:                  srcs,
		AidlRoot:              aidlRoot,
		ImportsWithoutVersion: i.properties.ImportsWithoutVersion,
		IsToT:                 version == i.nextVersion(),
		Stability:             i.properties.Stability,
		Lang:                  langRust,
		BaseName:              i.ModuleBase.Name(),
		Version:               i.versionForAidlGenRule(version),
		Unstable:              i.properties.Unstable,
		Visibility:            srcsVisibility(mctx, langRust),
		Flags:                 i.flagsForAidlGenRule(version),
	})

	versionedRustName := fixRustName(i.versionedName(version))
	rustCrateName := fixRustName(i.ModuleBase.Name())

	mctx.CreateModule(aidlRustLibraryFactory, &rustProperties{
		Name:           proptools.StringPtr(rustModuleGen),
		Crate_name:     rustCrateName,
		Stem:           proptools.StringPtr("lib" + versionedRustName),
		Defaults:       []string{"aidl-rust-module-defaults"},
		Host_supported: i.properties.Host_supported,
		Apex_available: i.properties.Backend.Rust.Apex_available,
		Target:         rustTargetProperties{Darwin: darwinProperties{Enabled: proptools.BoolPtr(false)}},
	}, &rust.SourceProviderProperties{
		Source_stem: proptools.StringPtr(versionedRustName),
	}, &aidlRustSourceProviderProperties{
		SourceGen:         rustSourceGen,
		Imports:           i.properties.Imports,
		Version:           version,
		AidlInterfaceName: i.ModuleBase.Name(),
	})

	return rustModuleGen
}

// This function returns module name with version. Assume that there is foo of which latest version is 2
// Version -> Module name
// "1"->foo-V1
// "2"->foo-V2
// "3"->foo-V3
// And assume that there is 'bar' which is an 'unstable' interface.
// ""->bar
func (i *aidlInterface) versionedName(version string) string {
	name := i.ModuleBase.Name()
	if version == "" {
		return name
	}
	return name + "-V" + version
}

func (i *aidlInterface) srcsForVersion(mctx android.LoadHookContext, version string) (srcs []string, aidlRoot string) {
	if version == i.nextVersion() {
		return i.properties.Srcs, i.properties.Local_include_dir
	} else {
		aidlRoot = filepath.Join(aidlApiDir, i.ModuleBase.Name(), version)
		full_paths, err := mctx.GlobWithDeps(filepath.Join(mctx.ModuleDir(), aidlRoot, "**/*.aidl"), nil)
		if err != nil {
			panic(err)
		}
		for _, path := range full_paths {
			// Here, we need path local to the module
			srcs = append(srcs, strings.TrimPrefix(path, mctx.ModuleDir()+"/"))
		}
		return srcs, aidlRoot
	}
}

func (i *aidlInterface) versionForAidlGenRule(version string) string {
	if !i.hasVersion() {
		return ""
	}
	return version
}

func (i *aidlInterface) flagsForAidlGenRule(version string) (flags []string) {
	flags = append(flags, i.properties.Flags...)
	// For ToT, turn on "-Weverything" (enable all warnings)
	if version == i.nextVersion() {
		flags = append(flags, "-Weverything")
	}
	return
}

func (i *aidlInterface) isModuleForVndk(version string) bool {
	if i.properties.Vndk_use_version != nil {
		if !i.hasVersion() {
			panic("does not make sense, vndk_use_version specififed")
		}
		// Will be exactly one of the version numbers
		return version == *i.properties.Vndk_use_version
	}

	// For an interface with no versions, this is the ToT interface.
	if !i.hasVersion() {
		return version == i.nextVersion()
	}

	return version == i.latestVersion()
}

// importing aidl_interface's version  | imported aidl_interface | imported aidl_interface's version
// --------------------------------------------------------------------------------------------------
// whatever                            | unstable                | unstable version
// ToT version(including unstable)     | whatever                | ToT version(unstable if unstable)
// otherwise                           | whatever                | the latest stable version
// In the case that import specifies the version which it wants to use, use that version.
func (i *aidlInterface) getImportWithVersion(version string, anImport string, config android.Config) string {
	if hasVersionSuffix(anImport) {
		return anImport
	}
	other := lookupInterface(anImport, config)
	if proptools.Bool(other.properties.Unstable) {
		return anImport
	}
	if version == i.nextVersion() || !other.hasVersion() {
		return other.versionedName(other.nextVersion())
	}
	return other.versionedName(other.latestVersion())
}

func aidlImplementationGeneratorFactory() android.Module {
	g := &aidlImplementationGenerator{}
	g.AddProperties(&g.properties)
	android.InitAndroidModule(g)
	return g
}

type aidlImplementationGenerator struct {
	android.ModuleBase
	properties aidlImplementationGeneratorProperties
}

type aidlImplementationGeneratorProperties struct {
	Lang              string
	AidlInterfaceName string
	Version           string
	ModuleProperties  []interface{}
}

func (g *aidlImplementationGenerator) DepsMutator(ctx android.BottomUpMutatorContext) {
}

func (g *aidlImplementationGenerator) GenerateAndroidBuildActions(ctx android.ModuleContext) {
}

func (g *aidlImplementationGenerator) GenerateImplementation(ctx android.TopDownMutatorContext) {
	i := lookupInterface(g.properties.AidlInterfaceName, ctx.Config())
	version := g.properties.Version
	lang := g.properties.Lang
	if g.properties.Lang == langJava {
		imports := make([]string, len(i.properties.Imports))
		for idx, anImport := range i.properties.Imports {
			imports[idx] = i.getImportWithVersion(version, anImport, ctx.Config()) + "-" + langJava
		}
		if p, ok := g.properties.ModuleProperties[0].(*javaProperties); ok {
			p.Static_libs = imports
		}
		ctx.CreateModule(java.LibraryFactory, g.properties.ModuleProperties...)
	} else {
		imports := make([]string, len(i.properties.Imports))
		for idx, anImport := range i.properties.Imports {
			imports[idx] = i.getImportWithVersion(version, anImport, ctx.Config()) + "-" + lang
		}
		if p, ok := g.properties.ModuleProperties[0].(*ccProperties); ok {
			p.Shared_libs = append(p.Shared_libs, imports...)
			p.Export_shared_lib_headers = append(p.Export_shared_lib_headers, imports...)
		}
		ctx.CreateModule(cc.LibraryFactory, g.properties.ModuleProperties...)
	}
}
