am 05d6f67f: Merge "Set host and device arches from product variables"

* commit '05d6f67ff75c319e4abe2d70984872f4b8407ac1':
  Set host and device arches from product variables
This commit is contained in:
Colin Cross 2015-09-18 01:02:28 +00:00 committed by Android Git Automerger
commit 76c62b912d
2 changed files with 160 additions and 49 deletions

View file

@ -44,6 +44,15 @@ var (
}
)
var archTypeMap = map[string]ArchType{
"arm": Arm,
"arm64": Arm64,
"mips": Mips,
"misp64": Mips64,
"x86": X86,
"x86_64": X86_64,
}
/*
Example blueprints file containing all variant property groups, with comment listing what type
of variants get properties in that group:
@ -198,7 +207,7 @@ type Arch struct {
ArchType ArchType
ArchVariant string
CpuVariant string
Abi string
Abi []string
}
func (a Arch) String() string {
@ -287,23 +296,6 @@ var hostOrDeviceName = map[HostOrDevice]string{
}
var (
armArch = Arch{
ArchType: Arm,
ArchVariant: "armv7-a-neon",
CpuVariant: "cortex-a15",
Abi: "armeabi-v7a",
}
arm64Arch = Arch{
ArchType: Arm64,
CpuVariant: "denver64",
Abi: "arm64-v8a",
}
x86Arch = Arch{
ArchType: X86,
}
x8664Arch = Arch{
ArchType: X86_64,
}
commonArch = Arch{
ArchType: Common,
}
@ -348,55 +340,45 @@ func ArchMutator(mctx blueprint.EarlyMutatorContext) {
return
}
// TODO: this is all hardcoded for arm64 primary, arm secondary for now
// Replace with a configuration file written by lunch or bootstrap
hostArches, deviceArches, err := decodeArchProductVariables(mctx.Config().(Config).ProductVariables)
if err != nil {
mctx.ModuleErrorf("%s", err.Error())
}
arches := []Arch{}
moduleArches := []Arch{}
multilib := module.base().commonProperties.Compile_multilib
if module.base().HostSupported() && module.base().HostOrDevice().Host() {
switch module.base().commonProperties.Compile_multilib {
case "common":
arches = append(arches, commonArch)
case "both":
arches = append(arches, x8664Arch, x86Arch)
case "first", "64":
arches = append(arches, x8664Arch)
case "32":
arches = append(arches, x86Arch)
default:
arches = append(arches, x8664Arch)
hostModuleArches, err := decodeMultilib(multilib, hostArches)
if err != nil {
mctx.ModuleErrorf("%s", err.Error())
}
moduleArches = append(moduleArches, hostModuleArches...)
}
if module.base().DeviceSupported() && module.base().HostOrDevice().Device() {
switch module.base().commonProperties.Compile_multilib {
case "common":
arches = append(arches, commonArch)
case "both":
arches = append(arches, arm64Arch, armArch)
case "first", "64":
arches = append(arches, arm64Arch)
case "32":
arches = append(arches, armArch)
default:
mctx.ModuleErrorf(`compile_multilib must be "both", "first", "32", or "64", found %q`,
module.base().commonProperties.Compile_multilib)
deviceModuleArches, err := decodeMultilib(multilib, deviceArches)
if err != nil {
mctx.ModuleErrorf("%s", err.Error())
}
moduleArches = append(moduleArches, deviceModuleArches...)
}
if len(arches) == 0 {
if len(moduleArches) == 0 {
return
}
archNames := []string{}
for _, arch := range arches {
for _, arch := range moduleArches {
archNames = append(archNames, arch.String())
}
modules := mctx.CreateVariations(archNames...)
for i, m := range modules {
m.(AndroidModule).base().SetArch(arches[i])
m.(AndroidModule).base().SetArch(moduleArches[i])
m.(AndroidModule).base().setArchProperties(mctx)
}
}
@ -612,3 +594,106 @@ func forEachInterface(v reflect.Value, f func(reflect.Value)) {
panic(fmt.Errorf("Unsupported kind %s", v.Kind()))
}
}
// Convert the arch product variables into a list of host and device Arch structs
func decodeArchProductVariables(variables productVariables) ([]Arch, []Arch, error) {
if variables.HostArch == nil {
return nil, nil, fmt.Errorf("No host primary architecture set")
}
hostArch, err := decodeArch(*variables.HostArch, nil, nil, nil)
if err != nil {
return nil, nil, err
}
hostArches := []Arch{hostArch}
if variables.HostSecondaryArch != nil {
hostSecondaryArch, err := decodeArch(*variables.HostSecondaryArch, nil, nil, nil)
if err != nil {
return nil, nil, err
}
hostArches = append(hostArches, hostSecondaryArch)
}
if variables.DeviceArch == nil {
return nil, nil, fmt.Errorf("No device primary architecture set")
}
deviceArch, err := decodeArch(*variables.DeviceArch, variables.DeviceArchVariant,
variables.DeviceCpuVariant, variables.DeviceAbi)
if err != nil {
return nil, nil, err
}
deviceArches := []Arch{deviceArch}
if variables.DeviceSecondaryArch != nil {
deviceSecondaryArch, err := decodeArch(*variables.DeviceSecondaryArch,
variables.DeviceSecondaryArchVariant, variables.DeviceSecondaryCpuVariant,
variables.DeviceSecondaryAbi)
if err != nil {
return nil, nil, err
}
deviceArches = append(deviceArches, deviceSecondaryArch)
}
return hostArches, deviceArches, nil
}
// Convert a set of strings from product variables into a single Arch struct
func decodeArch(arch string, archVariant, cpuVariant *string, abi *[]string) (Arch, error) {
stringPtr := func(p *string) string {
if p != nil {
return *p
}
return ""
}
slicePtr := func(p *[]string) []string {
if p != nil {
return *p
}
return nil
}
archType := archTypeMap[arch]
return Arch{
ArchType: archType,
ArchVariant: stringPtr(archVariant),
CpuVariant: stringPtr(cpuVariant),
Abi: slicePtr(abi),
}, nil
}
// Use the module multilib setting to select one or more arches from an arch list
func decodeMultilib(multilib string, arches []Arch) ([]Arch, error) {
buildArches := []Arch{}
switch multilib {
case "common":
buildArches = append(buildArches, commonArch)
case "both":
buildArches = append(buildArches, arches...)
case "first":
buildArches = append(buildArches, arches[0])
case "32":
for _, a := range arches {
if a.ArchType.Multilib == "lib32" {
buildArches = append(buildArches, a)
}
}
case "64":
for _, a := range arches {
if a.ArchType.Multilib == "lib64" {
buildArches = append(buildArches, a)
}
}
default:
return nil, fmt.Errorf(`compile_multilib must be "both", "first", "32", or "64", found %q`,
multilib)
//buildArches = append(buildArches, arches[0])
}
return buildArches, nil
}

View file

@ -57,6 +57,19 @@ type productVariables struct {
Device_uses_dlmalloc *bool `json:",omitempty"`
Dlmalloc_alignment *int `json:",omitempty"`
Platform_sdk_version *int
DeviceArch *string `json:",omitempty"`
DeviceArchVariant *string `json:",omitempty"`
DeviceCpuVariant *string `json:",omitempty"`
DeviceAbi *[]string `json:",omitempty"`
DeviceSecondaryArch *string `json:",omitempty"`
DeviceSecondaryArchVariant *string `json:",omitempty"`
DeviceSecondaryCpuVariant *string `json:",omitempty"`
DeviceSecondaryAbi *[]string `json:",omitempty"`
HostArch *string `json:",omitempty"`
HostSecondaryArch *string `json:",omitempty"`
}
func boolPtr(v bool) *bool {
@ -67,10 +80,23 @@ func intPtr(v int) *int {
return &v
}
func stringPtr(v string) *string {
return &v
}
func (productVariables) DefaultConfig() jsonConfigurable {
v := productVariables{
Device_uses_jemalloc: boolPtr(true),
Platform_sdk_version: intPtr(22),
Device_uses_jemalloc: boolPtr(true),
Platform_sdk_version: intPtr(22),
HostArch: stringPtr("x86_64"),
HostSecondaryArch: stringPtr("x86"),
DeviceArch: stringPtr("arm64"),
DeviceCpuVariant: stringPtr("denver64"),
DeviceAbi: &[]string{"arm64-v8a"},
DeviceSecondaryArch: stringPtr("arm"),
DeviceSecondaryArchVariant: stringPtr("armv7-a-neon"),
DeviceSecondaryCpuVariant: stringPtr("cortex-a15"),
DeviceSecondaryAbi: &[]string{"armeabi-v7a"},
}
return v
}