Merge "Fix propagating EMPTY_NINJA_FILE from multiproduct_kati to minibp"
diff --git a/TEST_MAPPING b/TEST_MAPPING
new file mode 100644
index 0000000..9f386ca
--- /dev/null
+++ b/TEST_MAPPING
@@ -0,0 +1,7 @@
+{
+ "imports": [
+ {
+ "path": "packages/modules/SdkExtensions"
+ }
+ ]
+}
diff --git a/android/apex.go b/android/apex.go
index fa50030..4618fe9 100644
--- a/android/apex.go
+++ b/android/apex.go
@@ -117,19 +117,6 @@
return false
}
-// InApexByBaseName tells whether this apex variant of the module is part of the given apexVariant
-// or not, where the APEX is specified by its canonical base name, i.e. typically beginning with
-// "com.android.". In particular this function doesn't differentiate between source and prebuilt
-// APEXes, where the latter may have "prebuilt_" prefixes.
-func (i ApexInfo) InApexVariantByBaseName(apexVariant string) bool {
- for _, a := range i.InApexVariants {
- if RemoveOptionalPrebuiltPrefix(a) == apexVariant {
- return true
- }
- }
- return false
-}
-
func (i ApexInfo) InApexModule(apexModuleName string) bool {
for _, a := range i.InApexModules {
if a == apexModuleName {
diff --git a/android/arch.go b/android/arch.go
index 10c827b..9ff439c 100644
--- a/android/arch.go
+++ b/android/arch.go
@@ -897,7 +897,7 @@
// Add the OS/Arch combinations, e.g. "android_arm64".
for _, archType := range osArchTypeMap[os] {
- targets = append(targets, os.Field+"_"+archType.Name)
+ targets = append(targets, GetCompoundTargetName(os, archType))
// Also add the special "linux_<arch>" and "bionic_<arch>" property structs.
if os.Linux() {
@@ -1217,6 +1217,10 @@
return getChildPropertyStruct(ctx, multilibProp, archType.Multilib, "multilib."+archType.Multilib)
}
+func GetCompoundTargetName(os OsType, arch ArchType) string {
+ return os.Field + "_" + arch.Name
+}
+
// Returns the structs corresponding to the properties specific to the given
// architecture and OS in archProperties.
func getArchProperties(ctx BaseMutatorContext, archProperties interface{}, arch Arch, os OsType, nativeBridgeEnabled bool) []reflect.Value {
@@ -1323,7 +1327,7 @@
// key: value,
// },
// },
- field := os.Field + "_" + archType.Name
+ field := GetCompoundTargetName(os, archType)
userFriendlyField := "target." + os.Name + "_" + archType.Name
if osArchProperties, ok := getChildPropertyStruct(ctx, targetProp, field, userFriendlyField); ok {
result = append(result, osArchProperties)
@@ -1950,19 +1954,47 @@
return archToProp
}
-// Returns the struct containing the properties specific to the given
-// architecture type. These look like this in Blueprint files:
-// target: {
-// android: {
-// key: value,
-// },
-// },
-// This struct will also contain sub-structs containing to the architecture/CPU
-// variants and features that themselves contain properties specific to those.
-func getTargetStruct(ctx ArchVariantContext, archProperties interface{}, os OsType) (reflect.Value, bool) {
- archPropValues := reflect.ValueOf(archProperties).Elem()
- targetProp := archPropValues.FieldByName("Target").Elem()
- return getChildPropertyStruct(ctx, targetProp, os.Field, os.Field)
+// Returns a struct matching the propertySet interface, containing properties specific to the targetName
+// For example, given these arguments:
+// propertySet = BaseCompilerProperties
+// targetName = "android_arm"
+// And given this Android.bp fragment:
+// target:
+// android_arm: {
+// srcs: ["foo.c"],
+// }
+// android_arm64: {
+// srcs: ["bar.c"],
+// }
+// }
+// This would return a BaseCompilerProperties with BaseCompilerProperties.Srcs = ["foo.c"]
+func getTargetStruct(ctx ArchVariantContext, propertySet interface{}, archProperties []interface{}, targetName string) interface{} {
+ propertyStructs := make([]reflect.Value, 0)
+ for _, archProperty := range archProperties {
+ archPropValues := reflect.ValueOf(archProperty).Elem()
+ targetProp := archPropValues.FieldByName("Target").Elem()
+ targetStruct, ok := getChildPropertyStruct(ctx, targetProp, targetName, targetName)
+ if ok {
+ propertyStructs = append(propertyStructs, targetStruct)
+ }
+ }
+
+ // Create a new instance of the requested property set
+ value := reflect.New(reflect.ValueOf(propertySet).Elem().Type()).Interface()
+
+ // Merge all the structs together
+ for _, propertyStruct := range propertyStructs {
+ mergePropertyStruct(ctx, value, propertyStruct)
+ }
+
+ return value
+}
+
+// Properties corresponds to e.g. Target: android: {...}
+// ArchProperties corresponds to e.g. Target: android_arm: {...}, android_arm64: {...}, ...
+type TargetProperties struct {
+ Properties interface{}
+ ArchProperties map[ArchType]interface{}
}
// GetTargetProperties returns a map of OS target (e.g. android, windows) to the
@@ -1974,13 +2006,15 @@
// the os-specific property value specified by the module if defined.
//
// Implemented in a way very similar to GetArchProperties().
-func (m *ModuleBase) GetTargetProperties(ctx ArchVariantContext, propertySet interface{}) map[OsType]interface{} {
- // Return value of the arch types to the prop values for that arch.
- osToProp := map[OsType]interface{}{}
+//
+// NOTE: "Target" == OS
+func (m *ModuleBase) GetTargetProperties(ctx ArchVariantContext, propertySet interface{}) map[OsType]TargetProperties {
+ // Return value of the target types to the prop values for that target.
+ targetToProp := map[OsType]TargetProperties{}
- // Nothing to do for non-OS/arch-specific modules.
+ // Nothing to do for non-target-specific modules.
if !m.ArchSpecific() {
- return osToProp
+ return targetToProp
}
dstType := reflect.ValueOf(propertySet).Type()
@@ -1998,33 +2032,26 @@
if archProperties == nil {
// This module does not have the property set requested
- return osToProp
+ return targetToProp
}
+ // For android, linux, ...
for _, os := range osTypeList {
if os == CommonOS {
// It looks like this OS value is not used in Blueprint files
continue
}
-
- propertyStructs := make([]reflect.Value, 0)
- for _, archProperty := range archProperties {
- targetStruct, ok := getTargetStruct(ctx, archProperty, os)
- if ok {
- propertyStructs = append(propertyStructs, targetStruct)
- }
+ targetProperties := TargetProperties{
+ Properties: getTargetStruct(ctx, propertySet, archProperties, os.Field),
+ ArchProperties: make(map[ArchType]interface{}),
}
-
- // Create a new instance of the requested property set
- value := reflect.New(reflect.ValueOf(propertySet).Elem().Type()).Interface()
-
- // Merge all the structs together
- for _, propertyStruct := range propertyStructs {
- mergePropertyStruct(ctx, value, propertyStruct)
+ // For arm, x86, ...
+ for _, arch := range osArchTypeMap[os] {
+ targetName := GetCompoundTargetName(os, arch)
+ targetProperties.ArchProperties[arch] = getTargetStruct(ctx, propertySet, archProperties, targetName)
}
-
- osToProp[os] = value
+ targetToProp[os] = targetProperties
}
- return osToProp
+ return targetToProp
}
diff --git a/android/bazel.go b/android/bazel.go
index ef770bf..4967b12 100644
--- a/android/bazel.go
+++ b/android/bazel.go
@@ -220,15 +220,8 @@
// Per-module denylist to opt modules out of mixed builds. Such modules will
// still be generated via bp2build.
mixedBuildsDisabledList = []string{
- "libc_common", // cparsons@ cc_library_static, depends on //bionic/libc:libc_nopthread
- "libc_common_static", // cparsons@ cc_library_static, depends on //bionic/libc:libc_common
- "libc_common_shared", // cparsons@ cc_library_static, depends on //bionic/libc:libc_common
- "libc_netbsd", // lberki@, cc_library_static, version script assignment of 'LIBC_PRIVATE' to symbol 'SHA1Final' failed: symbol not defined
- "libc_nopthread", // cparsons@ cc_library_static, version script assignment of 'LIBC' to symbol 'memcmp' failed: symbol not defined
- "libc_openbsd", // ruperts@, cc_library_static, OK for bp2build but error: duplicate symbol: strcpy for mixed builds
- "libarm-optimized-routines-string", // jingwen@, cc_library_static, OK for bp2build but b/186615213 (asflags not handled in bp2build), version script assignment of 'LIBC' to symbol 'memcmp' failed: symbol not defined (also for memrchr, strnlen)
- "fmtlib_ndk", // http://b/187040371, cc_library_static, OK for bp2build but format-inl.h:11:10: fatal error: 'cassert' file not found for mixed builds
- "libc_nomalloc", // cc_library_static, OK for bp2build but ld.lld: error: undefined symbol: pthread_mutex_lock (and others)
+ "libc_common_shared", // cparsons@ cc_library_static, breaks module `libc`.
+ "libc_nomalloc", // cparsons@ cc_library_static, breaks module `linker`
}
// Used for quicker lookups
diff --git a/android/variable.go b/android/variable.go
index cf74933..7658cdd 100644
--- a/android/variable.go
+++ b/android/variable.go
@@ -488,7 +488,10 @@
for os, targetProps := range moduleBase.GetTargetProperties(ctx, moduleBase.variableProperties) {
// GetTargetProperties is creating an instance of the requested type
// and productVariablesValues expects an interface, so no need to cast
- productVariableValues(targetProps, os.Name, &productConfigProperties)
+ productVariableValues(targetProps.Properties, os.Name, &productConfigProperties)
+ for arch, archProperties := range targetProps.ArchProperties {
+ productVariableValues(archProperties, os.Name+"_"+arch.Name, &productConfigProperties)
+ }
}
return productConfigProperties
diff --git a/apex/apex.go b/apex/apex.go
index 3448327..926085b 100644
--- a/apex/apex.go
+++ b/apex/apex.go
@@ -2020,7 +2020,7 @@
a.filesInfo = filesInfo
// Set suffix and primaryApexType depending on the ApexType
- buildFlattenedAsDefault := ctx.Config().FlattenApex() && !ctx.Config().UnbundledBuildApps()
+ buildFlattenedAsDefault := ctx.Config().FlattenApex()
switch a.properties.ApexType {
case imageApex:
if buildFlattenedAsDefault {
diff --git a/apex/apex_test.go b/apex/apex_test.go
index 4d00944..6a7c35c 100644
--- a/apex/apex_test.go
+++ b/apex/apex_test.go
@@ -709,6 +709,79 @@
}
}
+func TestApexManifestMinSdkVersion(t *testing.T) {
+ ctx := testApex(t, `
+ apex_defaults {
+ name: "my_defaults",
+ key: "myapex.key",
+ product_specific: true,
+ file_contexts: ":my-file-contexts",
+ updatable: false,
+ }
+ apex {
+ name: "myapex_30",
+ min_sdk_version: "30",
+ defaults: ["my_defaults"],
+ }
+
+ apex {
+ name: "myapex_current",
+ min_sdk_version: "current",
+ defaults: ["my_defaults"],
+ }
+
+ apex {
+ name: "myapex_none",
+ defaults: ["my_defaults"],
+ }
+
+ apex_key {
+ name: "myapex.key",
+ public_key: "testkey.avbpubkey",
+ private_key: "testkey.pem",
+ }
+
+ filegroup {
+ name: "my-file-contexts",
+ srcs: ["product_specific_file_contexts"],
+ }
+ `, withFiles(map[string][]byte{
+ "product_specific_file_contexts": nil,
+ }), android.FixtureModifyProductVariables(
+ func(variables android.FixtureProductVariables) {
+ variables.Unbundled_build = proptools.BoolPtr(true)
+ variables.Always_use_prebuilt_sdks = proptools.BoolPtr(false)
+ }), android.FixtureMergeEnv(map[string]string{
+ "UNBUNDLED_BUILD_TARGET_SDK_WITH_API_FINGERPRINT": "true",
+ }))
+
+ testCases := []struct {
+ module string
+ minSdkVersion string
+ }{
+ {
+ module: "myapex_30",
+ minSdkVersion: "30",
+ },
+ {
+ module: "myapex_current",
+ minSdkVersion: "Q.$$(cat out/soong/api_fingerprint.txt)",
+ },
+ {
+ module: "myapex_none",
+ minSdkVersion: "Q.$$(cat out/soong/api_fingerprint.txt)",
+ },
+ }
+ for _, tc := range testCases {
+ module := ctx.ModuleForTests(tc.module, "android_common_"+tc.module+"_image")
+ args := module.Rule("apexRule").Args
+ optFlags := args["opt_flags"]
+ if !strings.Contains(optFlags, "--min_sdk_version "+tc.minSdkVersion) {
+ t.Errorf("%s: Expected min_sdk_version=%s, got: %s", tc.module, tc.minSdkVersion, optFlags)
+ }
+ }
+}
+
func TestBasicZipApex(t *testing.T) {
ctx := testApex(t, `
apex {
diff --git a/apex/builder.go b/apex/builder.go
index da8841c..021e499 100644
--- a/apex/builder.go
+++ b/apex/builder.go
@@ -602,6 +602,11 @@
// codename
if moduleMinSdkVersion.IsCurrent() || moduleMinSdkVersion.IsNone() {
minSdkVersion = ctx.Config().DefaultAppTargetSdk(ctx).String()
+
+ if java.UseApiFingerprint(ctx) {
+ minSdkVersion = ctx.Config().PlatformSdkCodename() + fmt.Sprintf(".$$(cat %s)", java.ApiFingerprintPath(ctx).String())
+ implicitInputs = append(implicitInputs, java.ApiFingerprintPath(ctx))
+ }
}
// apex module doesn't have a concept of target_sdk_version, hence for the time
// being targetSdkVersion == default targetSdkVersion of the branch.
@@ -611,10 +616,6 @@
targetSdkVersion = ctx.Config().PlatformSdkCodename() + fmt.Sprintf(".$$(cat %s)", java.ApiFingerprintPath(ctx).String())
implicitInputs = append(implicitInputs, java.ApiFingerprintPath(ctx))
}
- if java.UseApiFingerprint(ctx) {
- minSdkVersion = ctx.Config().PlatformSdkCodename() + fmt.Sprintf(".$$(cat %s)", java.ApiFingerprintPath(ctx).String())
- implicitInputs = append(implicitInputs, java.ApiFingerprintPath(ctx))
- }
optFlags = append(optFlags, "--target_sdk_version "+targetSdkVersion)
optFlags = append(optFlags, "--min_sdk_version "+minSdkVersion)
diff --git a/apex/prebuilt.go b/apex/prebuilt.go
index 6125ef5..81bfc86 100644
--- a/apex/prebuilt.go
+++ b/apex/prebuilt.go
@@ -228,10 +228,11 @@
})
// Create an ApexInfo for the prebuilt_apex.
+ apexVariationName := android.RemoveOptionalPrebuiltPrefix(mctx.ModuleName())
apexInfo := android.ApexInfo{
- ApexVariationName: android.RemoveOptionalPrebuiltPrefix(mctx.ModuleName()),
- InApexVariants: []string{mctx.ModuleName()},
- InApexModules: []string{mctx.ModuleName()},
+ ApexVariationName: apexVariationName,
+ InApexVariants: []string{apexVariationName},
+ InApexModules: []string{apexVariationName},
ApexContents: []*android.ApexContents{apexContents},
ForPrebuiltApex: true,
}
diff --git a/bazel/properties.go b/bazel/properties.go
index 6ecf6ca..b2d68da 100644
--- a/bazel/properties.go
+++ b/bazel/properties.go
@@ -140,7 +140,6 @@
// Return all needles in a given haystack, where needleFn is true for needles.
func FilterLabelList(haystack LabelList, needleFn func(string) bool) LabelList {
var includes []Label
-
for _, inc := range haystack.Includes {
if needleFn(inc.Label) {
includes = append(includes, inc)
@@ -160,7 +159,12 @@
}
for os := range PlatformOsMap {
- result.SetValueForOS(os, FilterLabelList(haystack.GetValueForOS(os), needleFn))
+ result.SetOsValueForTarget(os, FilterLabelList(haystack.GetOsValueForTarget(os), needleFn))
+
+ // TODO(b/187530594): Should we handle arch=CONDITIONS_DEFAULT here? (not in ArchValues)
+ for _, arch := range AllArches {
+ result.SetOsArchValueForTarget(os, arch, FilterLabelList(haystack.GetOsArchValueForTarget(os, arch), needleFn))
+ }
}
return result
@@ -176,8 +180,12 @@
}
for os := range PlatformOsMap {
- result.SetValueForOS(os,
- SubtractBazelLabelList(haystack.GetValueForOS(os), needle.GetValueForOS(os)))
+ result.SetOsValueForTarget(os, SubtractBazelLabelList(haystack.GetOsValueForTarget(os), needle.GetOsValueForTarget(os)))
+
+ // TODO(b/187530594): Should we handle arch=CONDITIONS_DEFAULT here? (not in ArchValues)
+ for _, arch := range AllArches {
+ result.SetOsArchValueForTarget(os, arch, SubtractBazelLabelList(haystack.GetOsArchValueForTarget(os, arch), needle.GetOsArchValueForTarget(os, arch)))
+ }
}
result.Value = SubtractBazelLabelList(haystack.Value, needle.Value)
@@ -241,6 +249,21 @@
OS_LINUX_BIONIC = "linux_bionic"
OS_WINDOWS = "windows"
+ // Targets in arch.go
+ TARGET_ANDROID_ARM = "android_arm"
+ TARGET_ANDROID_ARM64 = "android_arm64"
+ TARGET_ANDROID_X86 = "android_x86"
+ TARGET_ANDROID_X86_64 = "android_x86_64"
+ TARGET_DARWIN_X86_64 = "darwin_x86_64"
+ TARGET_FUCHSIA_ARM64 = "fuchsia_arm64"
+ TARGET_FUCHSIA_X86_64 = "fuchsia_x86_64"
+ TARGET_LINUX_X86 = "linux_glibc_x86"
+ TARGET_LINUX_x86_64 = "linux_glibc_x86_64"
+ TARGET_LINUX_BIONIC_ARM64 = "linux_bionic_arm64"
+ TARGET_LINUX_BIONIC_X86_64 = "linux_bionic_x86_64"
+ TARGET_WINDOWS_X86 = "windows_x86"
+ TARGET_WINDOWS_X86_64 = "windows_x86_64"
+
// This is the string representation of the default condition wherever a
// configurable attribute is used in a select statement, i.e.
// //conditions:default for Bazel.
@@ -282,55 +305,200 @@
OS_WINDOWS: "//build/bazel/platforms/os:windows",
CONDITIONS_DEFAULT: ConditionsDefaultSelectKey, // The default condition of an os select map.
}
+
+ PlatformTargetMap = map[string]string{
+ TARGET_ANDROID_ARM: "//build/bazel/platforms/os_arch:android_arm",
+ TARGET_ANDROID_ARM64: "//build/bazel/platforms/os_arch:android_arm64",
+ TARGET_ANDROID_X86: "//build/bazel/platforms/os_arch:android_x86",
+ TARGET_ANDROID_X86_64: "//build/bazel/platforms/os_arch:android_x86_64",
+ TARGET_DARWIN_X86_64: "//build/bazel/platforms/os_arch:darwin_x86_64",
+ TARGET_FUCHSIA_ARM64: "//build/bazel/platforms/os_arch:fuchsia_arm64",
+ TARGET_FUCHSIA_X86_64: "//build/bazel/platforms/os_arch:fuchsia_x86_64",
+ TARGET_LINUX_X86: "//build/bazel/platforms/os_arch:linux_glibc_x86",
+ TARGET_LINUX_x86_64: "//build/bazel/platforms/os_arch:linux_glibc_x86_64",
+ TARGET_LINUX_BIONIC_ARM64: "//build/bazel/platforms/os_arch:linux_bionic_arm64",
+ TARGET_LINUX_BIONIC_X86_64: "//build/bazel/platforms/os_arch:linux_bionic_x86_64",
+ TARGET_WINDOWS_X86: "//build/bazel/platforms/os_arch:windows_x86",
+ TARGET_WINDOWS_X86_64: "//build/bazel/platforms/os_arch:windows_x86_64",
+ CONDITIONS_DEFAULT: ConditionsDefaultSelectKey, // The default condition of an os select map.
+ }
+
+ // TODO(b/187530594): Should we add CONDITIONS_DEFAULT here?
+ AllArches = []string{ARCH_ARM, ARCH_ARM64, ARCH_X86, ARCH_X86_64}
)
type Attribute interface {
HasConfigurableValues() bool
}
-// Represents an attribute whose value is a single label
-type LabelAttribute struct {
- Value Label
+type labelArchValues struct {
X86 Label
X86_64 Label
Arm Label
Arm64 Label
+
+ ConditionsDefault Label
+}
+
+type labelTargetValue struct {
+ // E.g. for android
+ OsValue Label
+
+ // E.g. for android_arm, android_arm64, ...
+ ArchValues labelArchValues
+}
+
+type labelTargetValues struct {
+ Android labelTargetValue
+ Darwin labelTargetValue
+ Fuchsia labelTargetValue
+ Linux labelTargetValue
+ LinuxBionic labelTargetValue
+ Windows labelTargetValue
+
+ ConditionsDefault labelTargetValue
+}
+
+// Represents an attribute whose value is a single label
+type LabelAttribute struct {
+ Value Label
+
+ ArchValues labelArchValues
+
+ TargetValues labelTargetValues
}
func (attr *LabelAttribute) GetValueForArch(arch string) Label {
- switch arch {
- case ARCH_ARM:
- return attr.Arm
- case ARCH_ARM64:
- return attr.Arm64
- case ARCH_X86:
- return attr.X86
- case ARCH_X86_64:
- return attr.X86_64
- case CONDITIONS_DEFAULT:
- return attr.Value
- default:
- panic("Invalid arch type")
+ var v *Label
+ if v = attr.archValuePtrs()[arch]; v == nil {
+ panic(fmt.Errorf("Unknown arch: %s", arch))
}
+ return *v
}
func (attr *LabelAttribute) SetValueForArch(arch string, value Label) {
- switch arch {
- case ARCH_ARM:
- attr.Arm = value
- case ARCH_ARM64:
- attr.Arm64 = value
- case ARCH_X86:
- attr.X86 = value
- case ARCH_X86_64:
- attr.X86_64 = value
- default:
- panic("Invalid arch type")
+ var v *Label
+ if v = attr.archValuePtrs()[arch]; v == nil {
+ panic(fmt.Errorf("Unknown arch: %s", arch))
+ }
+ *v = value
+}
+
+func (attr *LabelAttribute) archValuePtrs() map[string]*Label {
+ return map[string]*Label{
+ ARCH_X86: &attr.ArchValues.X86,
+ ARCH_X86_64: &attr.ArchValues.X86_64,
+ ARCH_ARM: &attr.ArchValues.Arm,
+ ARCH_ARM64: &attr.ArchValues.Arm64,
+ CONDITIONS_DEFAULT: &attr.ArchValues.ConditionsDefault,
}
}
func (attr LabelAttribute) HasConfigurableValues() bool {
- return attr.Arm.Label != "" || attr.Arm64.Label != "" || attr.X86.Label != "" || attr.X86_64.Label != ""
+ for arch := range PlatformArchMap {
+ if attr.GetValueForArch(arch).Label != "" {
+ return true
+ }
+ }
+
+ for os := range PlatformOsMap {
+ if attr.GetOsValueForTarget(os).Label != "" {
+ return true
+ }
+ // TODO(b/187530594): Should we also check arch=CONDITIONS_DEFAULT (not in AllArches)
+ for _, arch := range AllArches {
+ if attr.GetOsArchValueForTarget(os, arch).Label != "" {
+ return true
+ }
+ }
+ }
+ return false
+}
+
+func (attr *LabelAttribute) getValueForTarget(os string) labelTargetValue {
+ var v *labelTargetValue
+ if v = attr.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ return *v
+}
+
+func (attr *LabelAttribute) GetOsValueForTarget(os string) Label {
+ var v *labelTargetValue
+ if v = attr.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ return v.OsValue
+}
+
+func (attr *LabelAttribute) GetOsArchValueForTarget(os string, arch string) Label {
+ var v *labelTargetValue
+ if v = attr.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ switch arch {
+ case ARCH_X86:
+ return v.ArchValues.X86
+ case ARCH_X86_64:
+ return v.ArchValues.X86_64
+ case ARCH_ARM:
+ return v.ArchValues.Arm
+ case ARCH_ARM64:
+ return v.ArchValues.Arm64
+ case CONDITIONS_DEFAULT:
+ return v.ArchValues.ConditionsDefault
+ default:
+ panic(fmt.Errorf("Unknown arch: %s\n", arch))
+ }
+}
+
+func (attr *LabelAttribute) setValueForTarget(os string, value labelTargetValue) {
+ var v *labelTargetValue
+ if v = attr.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ *v = value
+}
+
+func (attr *LabelAttribute) SetOsValueForTarget(os string, value Label) {
+ var v *labelTargetValue
+ if v = attr.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ v.OsValue = value
+}
+
+func (attr *LabelAttribute) SetOsArchValueForTarget(os string, arch string, value Label) {
+ var v *labelTargetValue
+ if v = attr.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ switch arch {
+ case ARCH_X86:
+ v.ArchValues.X86 = value
+ case ARCH_X86_64:
+ v.ArchValues.X86_64 = value
+ case ARCH_ARM:
+ v.ArchValues.Arm = value
+ case ARCH_ARM64:
+ v.ArchValues.Arm64 = value
+ case CONDITIONS_DEFAULT:
+ v.ArchValues.ConditionsDefault = value
+ default:
+ panic(fmt.Errorf("Unknown arch: %s\n", arch))
+ }
+}
+
+func (attr *LabelAttribute) targetValuePtrs() map[string]*labelTargetValue {
+ return map[string]*labelTargetValue{
+ OS_ANDROID: &attr.TargetValues.Android,
+ OS_DARWIN: &attr.TargetValues.Darwin,
+ OS_FUCHSIA: &attr.TargetValues.Fuchsia,
+ OS_LINUX: &attr.TargetValues.Linux,
+ OS_LINUX_BIONIC: &attr.TargetValues.LinuxBionic,
+ OS_WINDOWS: &attr.TargetValues.Windows,
+ CONDITIONS_DEFAULT: &attr.TargetValues.ConditionsDefault,
+ }
}
// Arch-specific label_list typed Bazel attribute values. This should correspond
@@ -340,20 +508,36 @@
X86_64 LabelList
Arm LabelList
Arm64 LabelList
- Common LabelList
ConditionsDefault LabelList
}
-type labelListOsValues struct {
- Android LabelList
- Darwin LabelList
- Fuchsia LabelList
- Linux LabelList
- LinuxBionic LabelList
- Windows LabelList
+type labelListTargetValue struct {
+ // E.g. for android
+ OsValue LabelList
- ConditionsDefault LabelList
+ // E.g. for android_arm, android_arm64, ...
+ ArchValues labelListArchValues
+}
+
+func (target *labelListTargetValue) Append(other labelListTargetValue) {
+ target.OsValue.Append(other.OsValue)
+ target.ArchValues.X86.Append(other.ArchValues.X86)
+ target.ArchValues.X86_64.Append(other.ArchValues.X86_64)
+ target.ArchValues.Arm.Append(other.ArchValues.Arm)
+ target.ArchValues.Arm64.Append(other.ArchValues.Arm64)
+ target.ArchValues.ConditionsDefault.Append(other.ArchValues.ConditionsDefault)
+}
+
+type labelListTargetValues struct {
+ Android labelListTargetValue
+ Darwin labelListTargetValue
+ Fuchsia labelListTargetValue
+ Linux labelListTargetValue
+ LinuxBionic labelListTargetValue
+ Windows labelListTargetValue
+
+ ConditionsDefault labelListTargetValue
}
// LabelListAttribute is used to represent a list of Bazel labels as an
@@ -370,7 +554,7 @@
// The os-specific attribute label list values. Optional. If used, these
// are generated in a select statement and appended to the non-os specific
// label list Value.
- OsValues labelListOsValues
+ TargetValues labelListTargetValues
}
// MakeLabelListAttribute initializes a LabelListAttribute with the non-arch specific value.
@@ -389,10 +573,10 @@
}
for os := range PlatformOsMap {
- this := attrs.GetValueForOS(os)
- that := other.GetValueForOS(os)
+ this := attrs.getValueForTarget(os)
+ that := other.getValueForTarget(os)
this.Append(that)
- attrs.SetValueForOS(os, this)
+ attrs.setValueForTarget(os, this)
}
attrs.Value.Append(other.Value)
@@ -408,9 +592,15 @@
}
for os := range PlatformOsMap {
- if len(attrs.GetValueForOS(os).Includes) > 0 {
+ if len(attrs.GetOsValueForTarget(os).Includes) > 0 {
return true
}
+ // TODO(b/187530594): Should we also check arch=CONDITIONS_DEFAULT (not in AllArches)
+ for _, arch := range AllArches {
+ if len(attrs.GetOsArchValueForTarget(os, arch).Includes) > 0 {
+ return true
+ }
+ }
}
return false
}
@@ -443,36 +633,92 @@
*v = value
}
-func (attrs *LabelListAttribute) osValuePtrs() map[string]*LabelList {
- return map[string]*LabelList{
- OS_ANDROID: &attrs.OsValues.Android,
- OS_DARWIN: &attrs.OsValues.Darwin,
- OS_FUCHSIA: &attrs.OsValues.Fuchsia,
- OS_LINUX: &attrs.OsValues.Linux,
- OS_LINUX_BIONIC: &attrs.OsValues.LinuxBionic,
- OS_WINDOWS: &attrs.OsValues.Windows,
- CONDITIONS_DEFAULT: &attrs.OsValues.ConditionsDefault,
+func (attrs *LabelListAttribute) targetValuePtrs() map[string]*labelListTargetValue {
+ return map[string]*labelListTargetValue{
+ OS_ANDROID: &attrs.TargetValues.Android,
+ OS_DARWIN: &attrs.TargetValues.Darwin,
+ OS_FUCHSIA: &attrs.TargetValues.Fuchsia,
+ OS_LINUX: &attrs.TargetValues.Linux,
+ OS_LINUX_BIONIC: &attrs.TargetValues.LinuxBionic,
+ OS_WINDOWS: &attrs.TargetValues.Windows,
+ CONDITIONS_DEFAULT: &attrs.TargetValues.ConditionsDefault,
}
}
-// GetValueForOS returns the label_list attribute value for an OS target.
-func (attrs *LabelListAttribute) GetValueForOS(os string) LabelList {
- var v *LabelList
- if v = attrs.osValuePtrs()[os]; v == nil {
+func (attrs *LabelListAttribute) getValueForTarget(os string) labelListTargetValue {
+ var v *labelListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
panic(fmt.Errorf("Unknown os: %s", os))
}
return *v
}
-// SetValueForArch sets the label_list attribute value for an OS target.
-func (attrs *LabelListAttribute) SetValueForOS(os string, value LabelList) {
- var v *LabelList
- if v = attrs.osValuePtrs()[os]; v == nil {
+func (attrs *LabelListAttribute) GetOsValueForTarget(os string) LabelList {
+ var v *labelListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ return v.OsValue
+}
+
+func (attrs *LabelListAttribute) GetOsArchValueForTarget(os string, arch string) LabelList {
+ var v *labelListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ switch arch {
+ case ARCH_X86:
+ return v.ArchValues.X86
+ case ARCH_X86_64:
+ return v.ArchValues.X86_64
+ case ARCH_ARM:
+ return v.ArchValues.Arm
+ case ARCH_ARM64:
+ return v.ArchValues.Arm64
+ case CONDITIONS_DEFAULT:
+ return v.ArchValues.ConditionsDefault
+ default:
+ panic(fmt.Errorf("Unknown arch: %s\n", arch))
+ }
+}
+
+func (attrs *LabelListAttribute) setValueForTarget(os string, value labelListTargetValue) {
+ var v *labelListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
panic(fmt.Errorf("Unknown os: %s", os))
}
*v = value
}
+func (attrs *LabelListAttribute) SetOsValueForTarget(os string, value LabelList) {
+ var v *labelListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ v.OsValue = value
+}
+
+func (attrs *LabelListAttribute) SetOsArchValueForTarget(os string, arch string, value LabelList) {
+ var v *labelListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ switch arch {
+ case ARCH_X86:
+ v.ArchValues.X86 = value
+ case ARCH_X86_64:
+ v.ArchValues.X86_64 = value
+ case ARCH_ARM:
+ v.ArchValues.Arm = value
+ case ARCH_ARM64:
+ v.ArchValues.Arm64 = value
+ case CONDITIONS_DEFAULT:
+ v.ArchValues.ConditionsDefault = value
+ default:
+ panic(fmt.Errorf("Unknown arch: %s\n", arch))
+ }
+}
+
// StringListAttribute corresponds to the string_list Bazel attribute type with
// support for additional metadata, like configurations.
type StringListAttribute struct {
@@ -487,7 +733,7 @@
// The os-specific attribute string list values. Optional. If used, these
// are generated in a select statement and appended to the non-os specific
// label list Value.
- OsValues stringListOsValues
+ TargetValues stringListTargetValues
// list of product-variable string list values. Optional. if used, each will generate a select
// statement appended to the label list Value.
@@ -507,20 +753,36 @@
X86_64 []string
Arm []string
Arm64 []string
- Common []string
ConditionsDefault []string
}
-type stringListOsValues struct {
- Android []string
- Darwin []string
- Fuchsia []string
- Linux []string
- LinuxBionic []string
- Windows []string
+type stringListTargetValue struct {
+ // E.g. for android
+ OsValue []string
- ConditionsDefault []string
+ // E.g. for android_arm, android_arm64, ...
+ ArchValues stringListArchValues
+}
+
+func (target *stringListTargetValue) Append(other stringListTargetValue) {
+ target.OsValue = append(target.OsValue, other.OsValue...)
+ target.ArchValues.X86 = append(target.ArchValues.X86, other.ArchValues.X86...)
+ target.ArchValues.X86_64 = append(target.ArchValues.X86_64, other.ArchValues.X86_64...)
+ target.ArchValues.Arm = append(target.ArchValues.Arm, other.ArchValues.Arm...)
+ target.ArchValues.Arm64 = append(target.ArchValues.Arm64, other.ArchValues.Arm64...)
+ target.ArchValues.ConditionsDefault = append(target.ArchValues.ConditionsDefault, other.ArchValues.ConditionsDefault...)
+}
+
+type stringListTargetValues struct {
+ Android stringListTargetValue
+ Darwin stringListTargetValue
+ Fuchsia stringListTargetValue
+ Linux stringListTargetValue
+ LinuxBionic stringListTargetValue
+ Windows stringListTargetValue
+
+ ConditionsDefault stringListTargetValue
}
// Product Variable values for StringListAttribute
@@ -545,9 +807,16 @@
}
for os := range PlatformOsMap {
- if len(attrs.GetValueForOS(os)) > 0 {
+ if len(attrs.GetOsValueForTarget(os)) > 0 {
return true
}
+ // TODO(b/187530594): Should we also check arch=CONDITIONS_DEFAULT? (Not in AllArches)
+ for _, arch := range AllArches {
+ if len(attrs.GetOsArchValueForTarget(os, arch)) > 0 {
+ return true
+ }
+
+ }
}
return len(attrs.ProductValues) > 0
@@ -581,31 +850,58 @@
*v = value
}
-func (attrs *StringListAttribute) osValuePtrs() map[string]*[]string {
- return map[string]*[]string{
- OS_ANDROID: &attrs.OsValues.Android,
- OS_DARWIN: &attrs.OsValues.Darwin,
- OS_FUCHSIA: &attrs.OsValues.Fuchsia,
- OS_LINUX: &attrs.OsValues.Linux,
- OS_LINUX_BIONIC: &attrs.OsValues.LinuxBionic,
- OS_WINDOWS: &attrs.OsValues.Windows,
- CONDITIONS_DEFAULT: &attrs.OsValues.ConditionsDefault,
+func (attrs *StringListAttribute) targetValuePtrs() map[string]*stringListTargetValue {
+ return map[string]*stringListTargetValue{
+ OS_ANDROID: &attrs.TargetValues.Android,
+ OS_DARWIN: &attrs.TargetValues.Darwin,
+ OS_FUCHSIA: &attrs.TargetValues.Fuchsia,
+ OS_LINUX: &attrs.TargetValues.Linux,
+ OS_LINUX_BIONIC: &attrs.TargetValues.LinuxBionic,
+ OS_WINDOWS: &attrs.TargetValues.Windows,
+ CONDITIONS_DEFAULT: &attrs.TargetValues.ConditionsDefault,
}
}
-// GetValueForOS returns the string_list attribute value for an OS target.
-func (attrs *StringListAttribute) GetValueForOS(os string) []string {
- var v *[]string
- if v = attrs.osValuePtrs()[os]; v == nil {
+func (attrs *StringListAttribute) getValueForTarget(os string) stringListTargetValue {
+ var v *stringListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
panic(fmt.Errorf("Unknown os: %s", os))
}
return *v
}
-// SetValueForArch sets the string_list attribute value for an OS target.
-func (attrs *StringListAttribute) SetValueForOS(os string, value []string) {
- var v *[]string
- if v = attrs.osValuePtrs()[os]; v == nil {
+func (attrs *StringListAttribute) GetOsValueForTarget(os string) []string {
+ var v *stringListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ return v.OsValue
+}
+
+func (attrs *StringListAttribute) GetOsArchValueForTarget(os string, arch string) []string {
+ var v *stringListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ switch arch {
+ case ARCH_X86:
+ return v.ArchValues.X86
+ case ARCH_X86_64:
+ return v.ArchValues.X86_64
+ case ARCH_ARM:
+ return v.ArchValues.Arm
+ case ARCH_ARM64:
+ return v.ArchValues.Arm64
+ case CONDITIONS_DEFAULT:
+ return v.ArchValues.ConditionsDefault
+ default:
+ panic(fmt.Errorf("Unknown arch: %s\n", arch))
+ }
+}
+
+func (attrs *StringListAttribute) setValueForTarget(os string, value stringListTargetValue) {
+ var v *stringListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
panic(fmt.Errorf("Unknown os: %s", os))
}
*v = value
@@ -617,6 +913,35 @@
return vals
}
+func (attrs *StringListAttribute) SetOsValueForTarget(os string, value []string) {
+ var v *stringListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ v.OsValue = value
+}
+
+func (attrs *StringListAttribute) SetOsArchValueForTarget(os string, arch string, value []string) {
+ var v *stringListTargetValue
+ if v = attrs.targetValuePtrs()[os]; v == nil {
+ panic(fmt.Errorf("Unknown os: %s", os))
+ }
+ switch arch {
+ case ARCH_X86:
+ v.ArchValues.X86 = value
+ case ARCH_X86_64:
+ v.ArchValues.X86_64 = value
+ case ARCH_ARM:
+ v.ArchValues.Arm = value
+ case ARCH_ARM64:
+ v.ArchValues.Arm64 = value
+ case CONDITIONS_DEFAULT:
+ v.ArchValues.ConditionsDefault = value
+ default:
+ panic(fmt.Errorf("Unknown arch: %s\n", arch))
+ }
+}
+
// Append appends all values, including os and arch specific ones, from another
// StringListAttribute to this StringListAttribute
func (attrs *StringListAttribute) Append(other StringListAttribute) {
@@ -628,10 +953,10 @@
}
for os := range PlatformOsMap {
- this := attrs.GetValueForOS(os)
- that := other.GetValueForOS(os)
- this = append(this, that...)
- attrs.SetValueForOS(os, this)
+ this := attrs.getValueForTarget(os)
+ that := other.getValueForTarget(os)
+ this.Append(that)
+ attrs.setValueForTarget(os, this)
}
productValues := make(map[string][]string, 0)
@@ -668,6 +993,6 @@
// TryVariableSubstitution, replace string substitution formatting within s with Starlark
// string.format compatible tag for productVariable.
func TryVariableSubstitution(s string, productVariable string) (string, bool) {
- sub := productVariableSubstitutionPattern.ReplaceAllString(s, "{"+productVariable+"}")
+ sub := productVariableSubstitutionPattern.ReplaceAllString(s, "$("+productVariable+")")
return sub, s != sub
}
diff --git a/bp2build/build_conversion.go b/bp2build/build_conversion.go
index 7a73e18..6bdfc0e 100644
--- a/bp2build/build_conversion.go
+++ b/bp2build/build_conversion.go
@@ -445,7 +445,7 @@
return prettyPrint(propertyValue.Elem(), indent)
case reflect.Slice:
if propertyValue.Len() == 0 {
- return "", nil
+ return "[]", nil
}
if propertyValue.Len() == 1 {
@@ -568,6 +568,9 @@
return true
}
default:
+ if !value.IsValid() {
+ return true
+ }
zeroValue := reflect.Zero(value.Type())
result := value.Interface() == zeroValue.Interface()
return result
diff --git a/bp2build/cc_library_conversion_test.go b/bp2build/cc_library_conversion_test.go
index 350bac1..b87d713 100644
--- a/bp2build/cc_library_conversion_test.go
+++ b/bp2build/cc_library_conversion_test.go
@@ -400,6 +400,141 @@
})
}
+func TestCcLibrarySharedStaticPropsInArch(t *testing.T) {
+ runCcLibraryTestCase(t, bp2buildTestCase{
+ description: "cc_library shared/static props in arch",
+ moduleTypeUnderTest: "cc_library",
+ moduleTypeUnderTestFactory: cc.LibraryFactory,
+ moduleTypeUnderTestBp2BuildMutator: cc.CcLibraryBp2Build,
+ depsMutators: []android.RegisterMutatorFunc{cc.RegisterDepsBp2Build},
+ dir: "foo/bar",
+ filesystem: map[string]string{
+ "foo/bar/arm.cpp": "",
+ "foo/bar/x86.cpp": "",
+ "foo/bar/sharedonly.cpp": "",
+ "foo/bar/staticonly.cpp": "",
+ "foo/bar/Android.bp": `
+cc_library {
+ name: "a",
+ arch: {
+ arm: {
+ shared: {
+ srcs: ["arm_shared.cpp"],
+ cflags: ["-DARM_SHARED"],
+ static_libs: ["arm_static_dep_for_shared"],
+ whole_static_libs: ["arm_whole_static_dep_for_shared"],
+ shared_libs: ["arm_shared_dep_for_shared"],
+ },
+ },
+ x86: {
+ static: {
+ srcs: ["x86_static.cpp"],
+ cflags: ["-DX86_STATIC"],
+ static_libs: ["x86_dep_for_static"],
+ },
+ },
+ },
+ target: {
+ android: {
+ shared: {
+ srcs: ["android_shared.cpp"],
+ cflags: ["-DANDROID_SHARED"],
+ static_libs: ["android_dep_for_shared"],
+ },
+ },
+ android_arm: {
+ shared: {
+ cflags: ["-DANDROID_ARM_SHARED"],
+ },
+ },
+ },
+ srcs: ["both.cpp"],
+ cflags: ["bothflag"],
+ static_libs: ["static_dep_for_both"],
+ static: {
+ srcs: ["staticonly.cpp"],
+ cflags: ["staticflag"],
+ static_libs: ["static_dep_for_static"],
+ },
+ shared: {
+ srcs: ["sharedonly.cpp"],
+ cflags: ["sharedflag"],
+ static_libs: ["static_dep_for_shared"],
+ },
+ bazel_module: { bp2build_available: true },
+}
+
+cc_library_static { name: "static_dep_for_shared" }
+cc_library_static { name: "static_dep_for_static" }
+cc_library_static { name: "static_dep_for_both" }
+
+cc_library_static { name: "arm_static_dep_for_shared" }
+cc_library_static { name: "arm_whole_static_dep_for_shared" }
+cc_library_static { name: "arm_shared_dep_for_shared" }
+
+cc_library_static { name: "x86_dep_for_static" }
+
+cc_library_static { name: "android_dep_for_shared" }
+`,
+ },
+ blueprint: soongCcLibraryPreamble,
+ expectedBazelTargets: []string{`cc_library(
+ name = "a",
+ copts = [
+ "bothflag",
+ "-Ifoo/bar",
+ "-I$(BINDIR)/foo/bar",
+ ],
+ dynamic_deps_for_shared = select({
+ "//build/bazel/platforms/arch:arm": [":arm_shared_dep_for_shared"],
+ "//conditions:default": [],
+ }),
+ implementation_deps = [":static_dep_for_both"],
+ shared_copts = ["sharedflag"] + select({
+ "//build/bazel/platforms/arch:arm": ["-DARM_SHARED"],
+ "//conditions:default": [],
+ }) + select({
+ "//build/bazel/platforms/os:android": ["-DANDROID_SHARED"],
+ "//conditions:default": [],
+ }) + select({
+ "//build/bazel/platforms/os_arch:android_arm": ["-DANDROID_ARM_SHARED"],
+ "//conditions:default": [],
+ }),
+ shared_srcs = ["sharedonly.cpp"] + select({
+ "//build/bazel/platforms/arch:arm": ["arm_shared.cpp"],
+ "//conditions:default": [],
+ }) + select({
+ "//build/bazel/platforms/os:android": ["android_shared.cpp"],
+ "//conditions:default": [],
+ }),
+ srcs = ["both.cpp"],
+ static_copts = ["staticflag"] + select({
+ "//build/bazel/platforms/arch:x86": ["-DX86_STATIC"],
+ "//conditions:default": [],
+ }),
+ static_deps_for_shared = [":static_dep_for_shared"] + select({
+ "//build/bazel/platforms/arch:arm": [":arm_static_dep_for_shared"],
+ "//conditions:default": [],
+ }) + select({
+ "//build/bazel/platforms/os:android": [":android_dep_for_shared"],
+ "//conditions:default": [],
+ }),
+ static_deps_for_static = [":static_dep_for_static"] + select({
+ "//build/bazel/platforms/arch:x86": [":x86_dep_for_static"],
+ "//conditions:default": [],
+ }),
+ static_srcs = ["staticonly.cpp"] + select({
+ "//build/bazel/platforms/arch:x86": ["x86_static.cpp"],
+ "//conditions:default": [],
+ }),
+ whole_archive_deps_for_shared = select({
+ "//build/bazel/platforms/arch:arm": [":arm_whole_static_dep_for_shared"],
+ "//conditions:default": [],
+ }),
+)`},
+ })
+}
+
func TestCcLibraryNonConfiguredVersionScript(t *testing.T) {
runCcLibraryTestCase(t, bp2buildTestCase{
description: "cc_library non-configured version script",
@@ -673,3 +808,46 @@
)`},
})
}
+
+func TestCcLibraryLabelAttributeGetTargetProperties(t *testing.T) {
+ runCcLibraryTestCase(t, bp2buildTestCase{
+ description: "cc_library GetTargetProperties on a LabelAttribute",
+ moduleTypeUnderTest: "cc_library",
+ moduleTypeUnderTestFactory: cc.LibraryFactory,
+ moduleTypeUnderTestBp2BuildMutator: cc.CcLibraryBp2Build,
+ depsMutators: []android.RegisterMutatorFunc{cc.RegisterDepsBp2Build},
+ dir: "foo/bar",
+ filesystem: map[string]string{
+ "foo/bar/Android.bp": `
+ cc_library {
+ name: "a",
+ srcs: ["a.cpp"],
+ target: {
+ android_arm: {
+ version_script: "android_arm.map",
+ },
+ linux_bionic_arm64: {
+ version_script: "linux_bionic_arm64.map",
+ },
+ },
+
+ bazel_module: { bp2build_available: true },
+ }
+ `,
+ },
+ blueprint: soongCcLibraryPreamble,
+ expectedBazelTargets: []string{`cc_library(
+ name = "a",
+ copts = [
+ "-Ifoo/bar",
+ "-I$(BINDIR)/foo/bar",
+ ],
+ srcs = ["a.cpp"],
+ version_script = select({
+ "//build/bazel/platforms/os_arch:android_arm": "android_arm.map",
+ "//build/bazel/platforms/os_arch:linux_bionic_arm64": "linux_bionic_arm64.map",
+ "//conditions:default": None,
+ }),
+)`},
+ })
+}
diff --git a/bp2build/cc_library_static_conversion_test.go b/bp2build/cc_library_static_conversion_test.go
index b7245a7..da38adb 100644
--- a/bp2build/cc_library_static_conversion_test.go
+++ b/bp2build/cc_library_static_conversion_test.go
@@ -850,6 +850,84 @@
})
}
+func TestCcLibraryStaticOneArchEmpty(t *testing.T) {
+ runCcLibraryStaticTestCase(t, bp2buildTestCase{
+ description: "cc_library_static one arch empty",
+ moduleTypeUnderTest: "cc_library_static",
+ moduleTypeUnderTestFactory: cc.LibraryStaticFactory,
+ moduleTypeUnderTestBp2BuildMutator: cc.CcLibraryStaticBp2Build,
+ depsMutators: []android.RegisterMutatorFunc{cc.RegisterDepsBp2Build},
+ filesystem: map[string]string{
+ "common.cc": "",
+ "foo-no-arm.cc": "",
+ "foo-excluded.cc": "",
+ },
+ blueprint: soongCcLibraryStaticPreamble + `
+cc_library_static {
+ name: "foo_static",
+ srcs: ["common.cc", "foo-*.cc"],
+ exclude_srcs: ["foo-excluded.cc"],
+ arch: {
+ arm: { exclude_srcs: ["foo-no-arm.cc"] },
+ },
+}`,
+ expectedBazelTargets: []string{`cc_library_static(
+ name = "foo_static",
+ copts = [
+ "-I.",
+ "-I$(BINDIR)/.",
+ ],
+ linkstatic = True,
+ srcs = ["common.cc"] + select({
+ "//build/bazel/platforms/arch:arm": [],
+ "//conditions:default": ["foo-no-arm.cc"],
+ }),
+)`},
+ })
+}
+
+func TestCcLibraryStaticOneArchEmptyOtherSet(t *testing.T) {
+ runCcLibraryStaticTestCase(t, bp2buildTestCase{
+ description: "cc_library_static one arch empty other set",
+ moduleTypeUnderTest: "cc_library_static",
+ moduleTypeUnderTestFactory: cc.LibraryStaticFactory,
+ moduleTypeUnderTestBp2BuildMutator: cc.CcLibraryStaticBp2Build,
+ depsMutators: []android.RegisterMutatorFunc{cc.RegisterDepsBp2Build},
+ filesystem: map[string]string{
+ "common.cc": "",
+ "foo-no-arm.cc": "",
+ "x86-only.cc": "",
+ "foo-excluded.cc": "",
+ },
+ blueprint: soongCcLibraryStaticPreamble + `
+cc_library_static {
+ name: "foo_static",
+ srcs: ["common.cc", "foo-*.cc"],
+ exclude_srcs: ["foo-excluded.cc"],
+ arch: {
+ arm: { exclude_srcs: ["foo-no-arm.cc"] },
+ x86: { srcs: ["x86-only.cc"] },
+ },
+}`,
+ expectedBazelTargets: []string{`cc_library_static(
+ name = "foo_static",
+ copts = [
+ "-I.",
+ "-I$(BINDIR)/.",
+ ],
+ linkstatic = True,
+ srcs = ["common.cc"] + select({
+ "//build/bazel/platforms/arch:arm": [],
+ "//build/bazel/platforms/arch:x86": [
+ "foo-no-arm.cc",
+ "x86-only.cc",
+ ],
+ "//conditions:default": ["foo-no-arm.cc"],
+ }),
+)`},
+ })
+}
+
func TestCcLibraryStaticMultipleDepSameName(t *testing.T) {
runCcLibraryStaticTestCase(t, bp2buildTestCase{
description: "cc_library_static multiple dep same name panic",
@@ -1158,6 +1236,66 @@
})
}
+func TestCcLibraryStaticGetTargetProperties(t *testing.T) {
+ runCcLibraryStaticTestCase(t, bp2buildTestCase{
+
+ description: "cc_library_static complex GetTargetProperties",
+ moduleTypeUnderTest: "cc_library_static",
+ moduleTypeUnderTestFactory: cc.LibraryStaticFactory,
+ moduleTypeUnderTestBp2BuildMutator: cc.CcLibraryStaticBp2Build,
+ depsMutators: []android.RegisterMutatorFunc{cc.RegisterDepsBp2Build},
+ blueprint: soongCcLibraryStaticPreamble + `
+cc_library_static {
+ name: "foo_static",
+ target: {
+ android: {
+ srcs: ["android_src.c"],
+ },
+ android_arm: {
+ srcs: ["android_arm_src.c"],
+ },
+ android_arm64: {
+ srcs: ["android_arm64_src.c"],
+ },
+ android_x86: {
+ srcs: ["android_x86_src.c"],
+ },
+ android_x86_64: {
+ srcs: ["android_x86_64_src.c"],
+ },
+ linux_bionic_arm64: {
+ srcs: ["linux_bionic_arm64_src.c"],
+ },
+ linux_bionic_x86_64: {
+ srcs: ["linux_bionic_x86_64_src.c"],
+ },
+ },
+}`,
+ expectedBazelTargets: []string{`cc_library_static(
+ name = "foo_static",
+ copts = [
+ "-I.",
+ "-I$(BINDIR)/.",
+ ],
+ linkstatic = True,
+ srcs_c = select({
+ "//build/bazel/platforms/os:android": ["android_src.c"],
+ "//conditions:default": [],
+ }) + select({
+ "//build/bazel/platforms/os_arch:android_arm": ["android_arm_src.c"],
+ "//build/bazel/platforms/os_arch:android_arm64": ["android_arm64_src.c"],
+ "//build/bazel/platforms/os_arch:android_x86": ["android_x86_src.c"],
+ "//build/bazel/platforms/os_arch:android_x86_64": ["android_x86_64_src.c"],
+ "//conditions:default": [],
+ }) + select({
+ "//build/bazel/platforms/os_arch:linux_bionic_arm64": ["linux_bionic_arm64_src.c"],
+ "//build/bazel/platforms/os_arch:linux_bionic_x86_64": ["linux_bionic_x86_64_src.c"],
+ "//conditions:default": [],
+ }),
+)`},
+ })
+}
+
func TestCcLibraryStaticProductVariableSelects(t *testing.T) {
runCcLibraryStaticTestCase(t, bp2buildTestCase{
description: "cc_library_static product variable selects",
@@ -1274,3 +1412,37 @@
)`},
})
}
+
+func TestCcLibraryStaticProductVariableStringReplacement(t *testing.T) {
+ runCcLibraryStaticTestCase(t, bp2buildTestCase{
+ description: "cc_library_static product variable selects",
+ moduleTypeUnderTest: "cc_library_static",
+ moduleTypeUnderTestFactory: cc.LibraryStaticFactory,
+ moduleTypeUnderTestBp2BuildMutator: cc.CcLibraryStaticBp2Build,
+ depsMutators: []android.RegisterMutatorFunc{cc.RegisterDepsBp2Build},
+ filesystem: map[string]string{},
+ blueprint: soongCcLibraryStaticPreamble + `
+cc_library_static {
+ name: "foo_static",
+ srcs: ["common.c"],
+ product_variables: {
+ platform_sdk_version: {
+ asflags: ["-DPLATFORM_SDK_VERSION=%d"],
+ },
+ },
+} `,
+ expectedBazelTargets: []string{`cc_library_static(
+ name = "foo_static",
+ asflags = select({
+ "//build/bazel/product_variables:platform_sdk_version": ["-DPLATFORM_SDK_VERSION=$(Platform_sdk_version)"],
+ "//conditions:default": [],
+ }),
+ copts = [
+ "-I.",
+ "-I$(BINDIR)/.",
+ ],
+ linkstatic = True,
+ srcs_c = ["common.c"],
+)`},
+ })
+}
diff --git a/bp2build/cc_object_conversion_test.go b/bp2build/cc_object_conversion_test.go
index f7e94c2..57f75ea 100644
--- a/bp2build/cc_object_conversion_test.go
+++ b/bp2build/cc_object_conversion_test.go
@@ -210,7 +210,7 @@
expectedBazelTargets: []string{`cc_object(
name = "foo",
asflags = select({
- "//build/bazel/product_variables:platform_sdk_version": ["-DPLATFORM_SDK_VERSION={Platform_sdk_version}"],
+ "//build/bazel/product_variables:platform_sdk_version": ["-DPLATFORM_SDK_VERSION=$(Platform_sdk_version)"],
"//conditions:default": [],
}),
copts = ["-fno-addrsig"],
diff --git a/bp2build/configurability.go b/bp2build/configurability.go
index 9869c5d..7e1a298 100644
--- a/bp2build/configurability.go
+++ b/bp2build/configurability.go
@@ -27,12 +27,25 @@
}
osSelects := map[string]reflect.Value{}
- for os, selectKey := range bazel.PlatformOsMap {
- osSelects[selectKey] = reflect.ValueOf(list.GetValueForOS(os))
+ osArchSelects := make([]selects, 0)
+ for _, os := range android.SortedStringKeys(bazel.PlatformOsMap) {
+ selectKey := bazel.PlatformOsMap[os]
+ osSelects[selectKey] = reflect.ValueOf(list.GetOsValueForTarget(os))
+ archSelects := make(map[string]reflect.Value)
+ // TODO(b/187530594): Should we also check arch=CONDITIONS_DEFAULT? (not in AllArches)
+ for _, arch := range bazel.AllArches {
+ target := os + "_" + arch
+ selectKey := bazel.PlatformTargetMap[target]
+ archSelects[selectKey] = reflect.ValueOf(list.GetOsArchValueForTarget(os, arch))
+ }
+ osArchSelects = append(osArchSelects, archSelects)
}
if len(osSelects) > 0 {
selectValues = append(selectValues, osSelects)
}
+ if len(osArchSelects) > 0 {
+ selectValues = append(selectValues, osArchSelects...)
+ }
for _, pv := range list.SortedProductVariables() {
s := make(selects)
@@ -47,19 +60,67 @@
}
func getLabelValue(label bazel.LabelAttribute) (reflect.Value, []selects) {
- var value reflect.Value
- var archSelects selects
-
- if label.HasConfigurableValues() {
- archSelects = map[string]reflect.Value{}
- for arch, selectKey := range bazel.PlatformArchMap {
- archSelects[selectKey] = reflect.ValueOf(label.GetValueForArch(arch))
- }
- } else {
- value = reflect.ValueOf(label.Value)
+ value := reflect.ValueOf(label.Value)
+ if !label.HasConfigurableValues() {
+ return value, []selects{}
}
- return value, []selects{archSelects}
+ // Keep track of which arches and oses have been used in case we need to raise a warning
+ usedArches := make(map[string]bool)
+ usedOses := make(map[string]bool)
+
+ archSelects := map[string]reflect.Value{}
+ for arch, selectKey := range bazel.PlatformArchMap {
+ archSelects[selectKey] = reflect.ValueOf(label.GetValueForArch(arch))
+ if archSelects[selectKey].IsValid() && !isZero(archSelects[selectKey]) {
+ usedArches[arch] = true
+ }
+ }
+
+ osSelects := map[string]reflect.Value{}
+ for _, os := range android.SortedStringKeys(bazel.PlatformOsMap) {
+ selectKey := bazel.PlatformOsMap[os]
+ osSelects[selectKey] = reflect.ValueOf(label.GetOsValueForTarget(os))
+ if osSelects[selectKey].IsValid() && !isZero(osSelects[selectKey]) {
+ usedOses[os] = true
+ }
+ }
+
+ osArchSelects := make([]selects, 0)
+ for _, os := range android.SortedStringKeys(bazel.PlatformOsMap) {
+ archSelects := make(map[string]reflect.Value)
+ // TODO(b/187530594): Should we also check arch=CONDITIONS_DEFAULT? (not in AllArches)
+ for _, arch := range bazel.AllArches {
+ target := os + "_" + arch
+ selectKey := bazel.PlatformTargetMap[target]
+ archSelects[selectKey] = reflect.ValueOf(label.GetOsArchValueForTarget(os, arch))
+ if archSelects[selectKey].IsValid() && !isZero(archSelects[selectKey]) {
+ if _, ok := usedArches[arch]; ok {
+ fmt.Printf("WARNING: Same arch used twice in LabelAttribute select: arch '%s'\n", arch)
+ }
+ if _, ok := usedOses[os]; ok {
+ fmt.Printf("WARNING: Same os used twice in LabelAttribute select: os '%s'\n", os)
+ }
+ }
+ }
+ osArchSelects = append(osArchSelects, archSelects)
+ }
+
+ // Because we have to return a single Label, we can only use one select statement
+ combinedSelects := map[string]reflect.Value{}
+ for k, v := range archSelects {
+ combinedSelects[k] = v
+ }
+ for k, v := range osSelects {
+ combinedSelects[k] = v
+ }
+ for _, osArchSelect := range osArchSelects {
+ for k, v := range osArchSelect {
+ combinedSelects[k] = v
+ }
+ }
+
+ return value, []selects{combinedSelects}
}
func getLabelListValues(list bazel.LabelListAttribute) (reflect.Value, []selects) {
@@ -67,18 +128,55 @@
if !list.HasConfigurableValues() {
return value, []selects{}
}
+ var ret []selects
archSelects := map[string]reflect.Value{}
for arch, selectKey := range bazel.PlatformArchMap {
- archSelects[selectKey] = reflect.ValueOf(list.GetValueForArch(arch).Includes)
+ if use, value := labelListSelectValue(selectKey, list.GetValueForArch(arch)); use {
+ archSelects[selectKey] = value
+ }
+ }
+ if len(archSelects) > 0 {
+ ret = append(ret, archSelects)
}
osSelects := map[string]reflect.Value{}
- for os, selectKey := range bazel.PlatformOsMap {
- osSelects[selectKey] = reflect.ValueOf(list.GetValueForOS(os).Includes)
+ osArchSelects := []selects{}
+ for _, os := range android.SortedStringKeys(bazel.PlatformOsMap) {
+ selectKey := bazel.PlatformOsMap[os]
+ if use, value := labelListSelectValue(selectKey, list.GetOsValueForTarget(os)); use {
+ osSelects[selectKey] = value
+ }
+ selects := make(map[string]reflect.Value)
+ // TODO(b/187530594): Should we also check arch=CONDITIOSN_DEFAULT? (not in AllArches)
+ for _, arch := range bazel.AllArches {
+ target := os + "_" + arch
+ selectKey := bazel.PlatformTargetMap[target]
+ if use, value := labelListSelectValue(selectKey, list.GetOsArchValueForTarget(os, arch)); use {
+ selects[selectKey] = value
+ }
+ }
+ if len(selects) > 0 {
+ osArchSelects = append(osArchSelects, selects)
+ }
}
+ if len(osSelects) > 0 {
+ ret = append(ret, osSelects)
+ }
+ ret = append(ret, osArchSelects...)
- return value, []selects{archSelects, osSelects}
+ return value, ret
+}
+
+func labelListSelectValue(selectKey string, list bazel.LabelList) (bool, reflect.Value) {
+ if selectKey == bazel.ConditionsDefaultSelectKey || len(list.Includes) > 0 {
+ return true, reflect.ValueOf(list.Includes)
+ } else if len(list.Excludes) > 0 {
+ // if there is still an excludes -- we need to have an empty list for this select & use the
+ // value in conditions default Includes
+ return true, reflect.ValueOf([]string{})
+ }
+ return false, reflect.Zero(reflect.TypeOf([]string{}))
}
// prettyPrintAttribute converts an Attribute to its Bazel syntax. May contain
diff --git a/cc/bp2build.go b/cc/bp2build.go
index 9bf101e..fed9936 100644
--- a/cc/bp2build.go
+++ b/cc/bp2build.go
@@ -19,6 +19,8 @@
"android/soong/android"
"android/soong/bazel"
+
+ "github.com/google/blueprint/proptools"
)
// bp2build functions and helpers for converting cc_* modules to Bazel.
@@ -50,35 +52,51 @@
var allDeps []string
- for _, p := range module.GetTargetProperties(ctx, &BaseCompilerProperties{}) {
- // base compiler props
- if baseCompilerProps, ok := p.(*BaseCompilerProperties); ok {
+ for _, osProps := range module.GetTargetProperties(ctx, &BaseCompilerProperties{}) {
+ // os base compiler props
+ if baseCompilerProps, ok := osProps.Properties.(*BaseCompilerProperties); ok {
allDeps = append(allDeps, baseCompilerProps.Generated_headers...)
allDeps = append(allDeps, baseCompilerProps.Generated_sources...)
}
+ // os + arch base compiler props
+ for _, archProps := range osProps.ArchProperties {
+ if baseCompilerProps, ok := archProps.(*BaseCompilerProperties); ok {
+ allDeps = append(allDeps, baseCompilerProps.Generated_headers...)
+ allDeps = append(allDeps, baseCompilerProps.Generated_sources...)
+ }
+ }
}
- for _, p := range module.GetArchProperties(ctx, &BaseCompilerProperties{}) {
+ for _, props := range module.GetArchProperties(ctx, &BaseCompilerProperties{}) {
// arch specific compiler props
- if baseCompilerProps, ok := p.(*BaseCompilerProperties); ok {
+ if baseCompilerProps, ok := props.(*BaseCompilerProperties); ok {
allDeps = append(allDeps, baseCompilerProps.Generated_headers...)
allDeps = append(allDeps, baseCompilerProps.Generated_sources...)
}
}
- for _, p := range module.GetTargetProperties(ctx, &BaseLinkerProperties{}) {
- // arch specific linker props
- if baseLinkerProps, ok := p.(*BaseLinkerProperties); ok {
+ for _, osProps := range module.GetTargetProperties(ctx, &BaseLinkerProperties{}) {
+ // os specific linker props
+ if baseLinkerProps, ok := osProps.Properties.(*BaseLinkerProperties); ok {
allDeps = append(allDeps, baseLinkerProps.Header_libs...)
allDeps = append(allDeps, baseLinkerProps.Export_header_lib_headers...)
allDeps = append(allDeps, baseLinkerProps.Static_libs...)
allDeps = append(allDeps, baseLinkerProps.Whole_static_libs...)
}
+ // os + arch base compiler props
+ for _, archProps := range osProps.ArchProperties {
+ if baseLinkerProps, ok := archProps.(*BaseLinkerProperties); ok {
+ allDeps = append(allDeps, baseLinkerProps.Header_libs...)
+ allDeps = append(allDeps, baseLinkerProps.Export_header_lib_headers...)
+ allDeps = append(allDeps, baseLinkerProps.Static_libs...)
+ allDeps = append(allDeps, baseLinkerProps.Whole_static_libs...)
+ }
+ }
}
- for _, p := range module.GetArchProperties(ctx, &BaseLinkerProperties{}) {
+ for _, props := range module.GetArchProperties(ctx, &BaseLinkerProperties{}) {
// arch specific linker props
- if baseLinkerProps, ok := p.(*BaseLinkerProperties); ok {
+ if baseLinkerProps, ok := props.(*BaseLinkerProperties); ok {
allDeps = append(allDeps, baseLinkerProps.Header_libs...)
allDeps = append(allDeps, baseLinkerProps.Export_header_lib_headers...)
allDeps = append(allDeps, baseLinkerProps.Static_libs...)
@@ -88,25 +106,63 @@
// Deps in the static: { .. } and shared: { .. } props of a cc_library.
if lib, ok := module.compiler.(*libraryDecorator); ok {
- allDeps = append(allDeps, lib.SharedProperties.Shared.Static_libs...)
- allDeps = append(allDeps, lib.SharedProperties.Shared.Whole_static_libs...)
- allDeps = append(allDeps, lib.SharedProperties.Shared.Shared_libs...)
+ appendDeps := func(deps []string, p StaticOrSharedProperties) []string {
+ deps = append(deps, p.Static_libs...)
+ deps = append(deps, p.Whole_static_libs...)
+ deps = append(deps, p.Shared_libs...)
+ return deps
+ }
- allDeps = append(allDeps, lib.StaticProperties.Static.Static_libs...)
- allDeps = append(allDeps, lib.StaticProperties.Static.Whole_static_libs...)
- allDeps = append(allDeps, lib.StaticProperties.Static.Shared_libs...)
+ allDeps = appendDeps(allDeps, lib.SharedProperties.Shared)
+ allDeps = appendDeps(allDeps, lib.StaticProperties.Static)
// TODO(b/186024507, b/186489250): Temporarily exclude adding
// system_shared_libs deps until libc and libm builds.
// allDeps = append(allDeps, lib.SharedProperties.Shared.System_shared_libs...)
// allDeps = append(allDeps, lib.StaticProperties.Static.System_shared_libs...)
+
+ // Deps in the target/arch nested static: { .. } and shared: { .. } props of a cc_library.
+ // target: { <target>: shared: { ... } }
+ for _, targetProps := range module.GetTargetProperties(ctx, &SharedProperties{}) {
+ if p, ok := targetProps.Properties.(*SharedProperties); ok {
+ allDeps = appendDeps(allDeps, p.Shared)
+ }
+ for _, archProperties := range targetProps.ArchProperties {
+ if p, ok := archProperties.(*SharedProperties); ok {
+ allDeps = appendDeps(allDeps, p.Shared)
+ }
+ }
+ }
+ // target: { <target>: static: { ... } }
+ for _, targetProps := range module.GetTargetProperties(ctx, &StaticProperties{}) {
+ if p, ok := targetProps.Properties.(*StaticProperties); ok {
+ allDeps = appendDeps(allDeps, p.Static)
+ }
+ for _, archProperties := range targetProps.ArchProperties {
+ if p, ok := archProperties.(*StaticProperties); ok {
+ allDeps = appendDeps(allDeps, p.Static)
+ }
+ }
+ }
+ // arch: { <arch>: shared: { ... } }
+ for _, properties := range module.GetArchProperties(ctx, &SharedProperties{}) {
+ if p, ok := properties.(*SharedProperties); ok {
+ allDeps = appendDeps(allDeps, p.Shared)
+ }
+ }
+ // arch: { <arch>: static: { ... } }
+ for _, properties := range module.GetArchProperties(ctx, &StaticProperties{}) {
+ if p, ok := properties.(*StaticProperties); ok {
+ allDeps = appendDeps(allDeps, p.Static)
+ }
+ }
}
ctx.AddDependency(module, nil, android.SortedUniqueStrings(allDeps)...)
}
// staticOrSharedAttributes are the Bazel-ified versions of StaticOrSharedProperties --
-// properities which apply to either the shared or static version of a cc_library module.
+// properties which apply to either the shared or static version of a cc_library module.
type staticOrSharedAttributes struct {
copts bazel.StringListAttribute
srcs bazel.LabelListAttribute
@@ -122,7 +178,7 @@
return staticOrSharedAttributes{}
}
- return bp2buildParseStaticOrSharedProps(ctx, lib.SharedProperties.Shared)
+ return bp2buildParseStaticOrSharedProps(ctx, module, lib, false)
}
// bp2buildParseStaticProps returns the attributes for the static variant of a cc_library.
@@ -132,30 +188,143 @@
return staticOrSharedAttributes{}
}
- return bp2buildParseStaticOrSharedProps(ctx, lib.StaticProperties.Static)
+ return bp2buildParseStaticOrSharedProps(ctx, module, lib, true)
}
-func bp2buildParseStaticOrSharedProps(ctx android.TopDownMutatorContext, props StaticOrSharedProperties) staticOrSharedAttributes {
- copts := bazel.StringListAttribute{Value: props.Cflags}
+func bp2buildParseStaticOrSharedProps(ctx android.TopDownMutatorContext, module *Module, lib *libraryDecorator, isStatic bool) staticOrSharedAttributes {
+ var props StaticOrSharedProperties
+ if isStatic {
+ props = lib.StaticProperties.Static
+ } else {
+ props = lib.SharedProperties.Shared
+ }
- srcs := bazel.LabelListAttribute{
- Value: android.BazelLabelForModuleSrc(ctx, props.Srcs)}
+ attrs := staticOrSharedAttributes{
+ copts: bazel.StringListAttribute{Value: props.Cflags},
+ srcs: bazel.LabelListAttribute{Value: android.BazelLabelForModuleSrc(ctx, props.Srcs)},
+ staticDeps: bazel.LabelListAttribute{Value: android.BazelLabelForModuleDeps(ctx, props.Static_libs)},
+ dynamicDeps: bazel.LabelListAttribute{Value: android.BazelLabelForModuleDeps(ctx, props.Shared_libs)},
+ wholeArchiveDeps: bazel.LabelListAttribute{Value: android.BazelLabelForModuleDeps(ctx, props.Whole_static_libs)},
+ }
- staticDeps := bazel.LabelListAttribute{
- Value: android.BazelLabelForModuleDeps(ctx, props.Static_libs)}
+ setArchAttrs := func(arch string, props StaticOrSharedProperties) {
+ attrs.copts.SetValueForArch(arch, props.Cflags)
+ attrs.srcs.SetValueForArch(arch, android.BazelLabelForModuleSrc(ctx, props.Srcs))
+ attrs.staticDeps.SetValueForArch(arch, android.BazelLabelForModuleDeps(ctx, props.Static_libs))
+ attrs.dynamicDeps.SetValueForArch(arch, android.BazelLabelForModuleDeps(ctx, props.Shared_libs))
+ attrs.wholeArchiveDeps.SetValueForArch(arch, android.BazelLabelForModuleDeps(ctx, props.Whole_static_libs))
+ }
- dynamicDeps := bazel.LabelListAttribute{
- Value: android.BazelLabelForModuleDeps(ctx, props.Shared_libs)}
+ setTargetAttrs := func(target string, props StaticOrSharedProperties) {
+ attrs.copts.SetOsValueForTarget(target, props.Cflags)
+ attrs.srcs.SetOsValueForTarget(target, android.BazelLabelForModuleSrc(ctx, props.Srcs))
+ attrs.staticDeps.SetOsValueForTarget(target, android.BazelLabelForModuleDeps(ctx, props.Static_libs))
+ attrs.dynamicDeps.SetOsValueForTarget(target, android.BazelLabelForModuleDeps(ctx, props.Shared_libs))
+ attrs.wholeArchiveDeps.SetOsValueForTarget(target, android.BazelLabelForModuleDeps(ctx, props.Whole_static_libs))
+ }
- wholeArchiveDeps := bazel.LabelListAttribute{
- Value: android.BazelLabelForModuleDeps(ctx, props.Whole_static_libs)}
+ setTargetArchAttrs := func(target, arch string, props StaticOrSharedProperties) {
+ attrs.copts.SetOsArchValueForTarget(target, arch, props.Cflags)
+ attrs.srcs.SetOsArchValueForTarget(target, arch, android.BazelLabelForModuleSrc(ctx, props.Srcs))
+ attrs.staticDeps.SetOsArchValueForTarget(target, arch, android.BazelLabelForModuleDeps(ctx, props.Static_libs))
+ attrs.dynamicDeps.SetOsArchValueForTarget(target, arch, android.BazelLabelForModuleDeps(ctx, props.Shared_libs))
+ attrs.wholeArchiveDeps.SetOsArchValueForTarget(target, arch, android.BazelLabelForModuleDeps(ctx, props.Whole_static_libs))
+ }
- return staticOrSharedAttributes{
- copts: copts,
- srcs: srcs,
- staticDeps: staticDeps,
- dynamicDeps: dynamicDeps,
- wholeArchiveDeps: wholeArchiveDeps,
+ if isStatic {
+ for arch, properties := range module.GetArchProperties(ctx, &StaticProperties{}) {
+ if staticOrSharedProps, ok := properties.(*StaticProperties); ok {
+ setArchAttrs(arch.Name, staticOrSharedProps.Static)
+ }
+ }
+ for target, p := range module.GetTargetProperties(ctx, &StaticProperties{}) {
+ if staticOrSharedProps, ok := p.Properties.(*StaticProperties); ok {
+ setTargetAttrs(target.Name, staticOrSharedProps.Static)
+ }
+ for arch, archProperties := range p.ArchProperties {
+ if staticOrSharedProps, ok := archProperties.(*StaticProperties); ok {
+ setTargetArchAttrs(target.Name, arch.Name, staticOrSharedProps.Static)
+ }
+ }
+ }
+ } else {
+ for arch, p := range module.GetArchProperties(ctx, &SharedProperties{}) {
+ if staticOrSharedProps, ok := p.(*SharedProperties); ok {
+ setArchAttrs(arch.Name, staticOrSharedProps.Shared)
+ }
+ }
+ for target, p := range module.GetTargetProperties(ctx, &SharedProperties{}) {
+ if staticOrSharedProps, ok := p.Properties.(*SharedProperties); ok {
+ setTargetAttrs(target.Name, staticOrSharedProps.Shared)
+ }
+ for arch, archProperties := range p.ArchProperties {
+ if staticOrSharedProps, ok := archProperties.(*SharedProperties); ok {
+ setTargetArchAttrs(target.Name, arch.Name, staticOrSharedProps.Shared)
+ }
+ }
+ }
+ }
+
+ return attrs
+}
+
+// Convenience struct to hold all attributes parsed from prebuilt properties.
+type prebuiltAttributes struct {
+ Src bazel.LabelAttribute
+}
+
+func Bp2BuildParsePrebuiltLibraryProps(ctx android.TopDownMutatorContext, module *Module) prebuiltAttributes {
+ prebuiltLibraryLinker := module.linker.(*prebuiltLibraryLinker)
+ prebuiltLinker := prebuiltLibraryLinker.prebuiltLinker
+
+ var srcLabelAttribute bazel.LabelAttribute
+
+ if len(prebuiltLinker.properties.Srcs) > 1 {
+ ctx.ModuleErrorf("Bp2BuildParsePrebuiltLibraryProps: Expected at most once source file\n")
+ }
+
+ if len(prebuiltLinker.properties.Srcs) == 1 {
+ srcLabelAttribute.Value = android.BazelLabelForModuleSrcSingle(ctx, prebuiltLinker.properties.Srcs[0])
+ for arch, props := range module.GetArchProperties(ctx, &prebuiltLinkerProperties{}) {
+ if prebuiltLinkerProperties, ok := props.(*prebuiltLinkerProperties); ok {
+ if len(prebuiltLinkerProperties.Srcs) > 1 {
+ ctx.ModuleErrorf("Bp2BuildParsePrebuiltLibraryProps: Expected at most once source file for arch %s\n", arch.Name)
+ }
+ if len(prebuiltLinkerProperties.Srcs) == 1 {
+ srcLabelAttribute.SetValueForArch(arch.Name, android.BazelLabelForModuleSrcSingle(ctx, prebuiltLinkerProperties.Srcs[0]))
+ }
+ }
+ }
+ }
+
+ for os, targetProperties := range module.GetTargetProperties(ctx, &prebuiltLinkerProperties{}) {
+ if prebuiltLinkerProperties, ok := targetProperties.Properties.(*prebuiltLinkerProperties); ok {
+ if len(prebuiltLinkerProperties.Srcs) > 1 {
+ ctx.ModuleErrorf("Bp2BuildParsePrebuiltLibraryProps: Expected at most once source file for os %s\n", os.Name)
+
+ }
+
+ if len(prebuiltLinkerProperties.Srcs) == 1 {
+ srcLabelAttribute.SetOsValueForTarget(os.Name, android.BazelLabelForModuleSrcSingle(ctx, prebuiltLinkerProperties.Srcs[0]))
+ }
+ }
+ for arch, archProperties := range targetProperties.ArchProperties {
+ if prebuiltLinkerProperties, ok := archProperties.(*prebuiltLinkerProperties); ok {
+ if len(prebuiltLinkerProperties.Srcs) > 1 {
+ ctx.ModuleErrorf("Bp2BuildParsePrebuiltLibraryProps: Expected at most once source file for os_arch %s_%s\n", os.Name, arch.Name)
+
+ }
+
+ if len(prebuiltLinkerProperties.Srcs) == 1 {
+ srcLabelAttribute.SetOsArchValueForTarget(os.Name, arch.Name, android.BazelLabelForModuleSrcSingle(ctx, prebuiltLinkerProperties.Srcs[0]))
+ }
+ }
+
+ }
+ }
+
+ return prebuiltAttributes{
+ Src: srcLabelAttribute,
}
}
@@ -309,31 +478,53 @@
// TODO(b/186153868): handle the case with multiple variant types, e.g. when arch and os are both used.
srcs.SetValueForArch(bazel.CONDITIONS_DEFAULT, defaultsSrcs)
- // Handle OS specific props.
- for os, props := range module.GetTargetProperties(ctx, &BaseCompilerProperties{}) {
- if baseCompilerProps, ok := props.(*BaseCompilerProperties); ok {
+ // Handle target specific properties.
+ for os, osProps := range module.GetTargetProperties(ctx, &BaseCompilerProperties{}) {
+ if baseCompilerProps, ok := osProps.Properties.(*BaseCompilerProperties); ok {
srcsList := parseSrcs(baseCompilerProps)
// TODO(b/186153868): add support for os-specific srcs and exclude_srcs
- srcs.SetValueForOS(os.Name, bazel.SubtractBazelLabelList(srcsList, baseSrcsLabelList))
- copts.SetValueForOS(os.Name, parseCopts(baseCompilerProps))
- asFlags.SetValueForOS(os.Name, parseCommandLineFlags(baseCompilerProps.Asflags))
- conlyFlags.SetValueForOS(os.Name, parseCommandLineFlags(baseCompilerProps.Conlyflags))
- cppFlags.SetValueForOS(os.Name, parseCommandLineFlags(baseCompilerProps.Cppflags))
+ if len(baseCompilerProps.Srcs) > 0 || len(baseCompilerProps.Exclude_srcs) > 0 {
+ srcs.SetOsValueForTarget(os.Name, bazel.SubtractBazelLabelList(srcsList, baseSrcsLabelList))
+ }
+ copts.SetOsValueForTarget(os.Name, parseCopts(baseCompilerProps))
+ asFlags.SetOsValueForTarget(os.Name, parseCommandLineFlags(baseCompilerProps.Asflags))
+ conlyFlags.SetOsValueForTarget(os.Name, parseCommandLineFlags(baseCompilerProps.Conlyflags))
+ cppFlags.SetOsValueForTarget(os.Name, parseCommandLineFlags(baseCompilerProps.Cppflags))
+ }
+ for arch, archProps := range osProps.ArchProperties {
+ if baseCompilerProps, ok := archProps.(*BaseCompilerProperties); ok {
+ srcsList := parseSrcs(baseCompilerProps)
+ // TODO(b/186153868): add support for os-specific srcs and exclude_srcs
+ if len(baseCompilerProps.Srcs) > 0 || len(baseCompilerProps.Exclude_srcs) > 0 {
+ srcs.SetOsArchValueForTarget(os.Name, arch.Name, bazel.SubtractBazelLabelList(srcsList, baseSrcsLabelList))
+ }
+ copts.SetOsArchValueForTarget(os.Name, arch.Name, parseCopts(baseCompilerProps))
+ asFlags.SetOsArchValueForTarget(os.Name, arch.Name, parseCommandLineFlags(baseCompilerProps.Asflags))
+ conlyFlags.SetOsArchValueForTarget(os.Name, arch.Name, parseCommandLineFlags(baseCompilerProps.Conlyflags))
+ cppFlags.SetOsArchValueForTarget(os.Name, arch.Name, parseCommandLineFlags(baseCompilerProps.Cppflags))
+ }
}
}
+ productVarPropNameToAttribute := map[string]*bazel.StringListAttribute{
+ "Cflags": &copts,
+ "Asflags": &asFlags,
+ "CppFlags": &cppFlags,
+ }
productVariableProps := android.ProductVariableProperties(ctx)
- if props, exists := productVariableProps["Cflags"]; exists {
- for _, prop := range props {
- flags, ok := prop.Property.([]string)
- if !ok {
- ctx.ModuleErrorf("Could not convert product variable cflag property")
+ for propName, attr := range productVarPropNameToAttribute {
+ if props, exists := productVariableProps[propName]; exists {
+ for _, prop := range props {
+ flags, ok := prop.Property.([]string)
+ if !ok {
+ ctx.ModuleErrorf("Could not convert product variable %s property", proptools.PropertyNameForField(propName))
+ }
+ newFlags, _ := bazel.TryVariableSubstitutions(flags, prop.ProductConfigVariable)
+ attr.ProductValues = append(attr.ProductValues, bazel.ProductVariableValues{
+ ProductVariable: prop.ProductConfigVariable,
+ Values: newFlags,
+ })
}
- newFlags, _ := bazel.TryVariableSubstitutions(flags, prop.ProductConfigVariable)
- copts.ProductValues = append(copts.ProductValues, bazel.ProductVariableValues{
- ProductVariable: prop.ProductConfigVariable,
- Values: newFlags,
- })
}
}
@@ -391,13 +582,18 @@
var linkopts bazel.StringListAttribute
var versionScript bazel.LabelAttribute
+ getLibs := func(baseLinkerProps *BaseLinkerProperties) []string {
+ libs := baseLinkerProps.Header_libs
+ libs = append(libs, baseLinkerProps.Static_libs...)
+ libs = android.SortedUniqueStrings(libs)
+ return libs
+ }
+
for _, linkerProps := range module.linker.linkerProps() {
if baseLinkerProps, ok := linkerProps.(*BaseLinkerProperties); ok {
- libs := baseLinkerProps.Header_libs
- libs = append(libs, baseLinkerProps.Static_libs...)
+ libs := getLibs(baseLinkerProps)
exportedLibs := baseLinkerProps.Export_header_lib_headers
wholeArchiveLibs := baseLinkerProps.Whole_static_libs
- libs = android.SortedUniqueStrings(libs)
deps = bazel.MakeLabelListAttribute(android.BazelLabelForModuleDeps(ctx, libs))
exportedDeps = bazel.MakeLabelListAttribute(android.BazelLabelForModuleDeps(ctx, exportedLibs))
linkopts.Value = getBp2BuildLinkerFlags(baseLinkerProps)
@@ -414,13 +610,11 @@
}
}
- for arch, p := range module.GetArchProperties(ctx, &BaseLinkerProperties{}) {
- if baseLinkerProps, ok := p.(*BaseLinkerProperties); ok {
- libs := baseLinkerProps.Header_libs
- libs = append(libs, baseLinkerProps.Static_libs...)
+ for arch, props := range module.GetArchProperties(ctx, &BaseLinkerProperties{}) {
+ if baseLinkerProps, ok := props.(*BaseLinkerProperties); ok {
+ libs := getLibs(baseLinkerProps)
exportedLibs := baseLinkerProps.Export_header_lib_headers
wholeArchiveLibs := baseLinkerProps.Whole_static_libs
- libs = android.SortedUniqueStrings(libs)
deps.SetValueForArch(arch.Name, android.BazelLabelForModuleDeps(ctx, libs))
exportedDeps.SetValueForArch(arch.Name, android.BazelLabelForModuleDeps(ctx, exportedLibs))
linkopts.SetValueForArch(arch.Name, getBp2BuildLinkerFlags(baseLinkerProps))
@@ -436,21 +630,42 @@
}
}
- for os, p := range module.GetTargetProperties(ctx, &BaseLinkerProperties{}) {
- if baseLinkerProps, ok := p.(*BaseLinkerProperties); ok {
- libs := baseLinkerProps.Header_libs
- libs = append(libs, baseLinkerProps.Static_libs...)
+ for os, targetProperties := range module.GetTargetProperties(ctx, &BaseLinkerProperties{}) {
+ if baseLinkerProps, ok := targetProperties.Properties.(*BaseLinkerProperties); ok {
+ libs := getLibs(baseLinkerProps)
exportedLibs := baseLinkerProps.Export_header_lib_headers
wholeArchiveLibs := baseLinkerProps.Whole_static_libs
- libs = android.SortedUniqueStrings(libs)
- wholeArchiveDeps.SetValueForOS(os.Name, android.BazelLabelForModuleDeps(ctx, wholeArchiveLibs))
- deps.SetValueForOS(os.Name, android.BazelLabelForModuleDeps(ctx, libs))
- exportedDeps.SetValueForOS(os.Name, android.BazelLabelForModuleDeps(ctx, exportedLibs))
+ wholeArchiveDeps.SetOsValueForTarget(os.Name, android.BazelLabelForModuleDeps(ctx, wholeArchiveLibs))
+ deps.SetOsValueForTarget(os.Name, android.BazelLabelForModuleDeps(ctx, libs))
+ exportedDeps.SetOsValueForTarget(os.Name, android.BazelLabelForModuleDeps(ctx, exportedLibs))
- linkopts.SetValueForOS(os.Name, getBp2BuildLinkerFlags(baseLinkerProps))
+ linkopts.SetOsValueForTarget(os.Name, getBp2BuildLinkerFlags(baseLinkerProps))
+
+ if baseLinkerProps.Version_script != nil {
+ versionScript.SetOsValueForTarget(os.Name, android.BazelLabelForModuleSrcSingle(ctx, *baseLinkerProps.Version_script))
+ }
sharedLibs := baseLinkerProps.Shared_libs
- dynamicDeps.SetValueForOS(os.Name, android.BazelLabelForModuleDeps(ctx, sharedLibs))
+ dynamicDeps.SetOsValueForTarget(os.Name, android.BazelLabelForModuleDeps(ctx, sharedLibs))
+ }
+ for arch, archProperties := range targetProperties.ArchProperties {
+ if baseLinkerProps, ok := archProperties.(*BaseLinkerProperties); ok {
+ libs := getLibs(baseLinkerProps)
+ exportedLibs := baseLinkerProps.Export_header_lib_headers
+ wholeArchiveLibs := baseLinkerProps.Whole_static_libs
+ wholeArchiveDeps.SetOsArchValueForTarget(os.Name, arch.Name, android.BazelLabelForModuleDeps(ctx, wholeArchiveLibs))
+ deps.SetOsArchValueForTarget(os.Name, arch.Name, android.BazelLabelForModuleDeps(ctx, libs))
+ exportedDeps.SetOsArchValueForTarget(os.Name, arch.Name, android.BazelLabelForModuleDeps(ctx, exportedLibs))
+
+ linkopts.SetOsArchValueForTarget(os.Name, arch.Name, getBp2BuildLinkerFlags(baseLinkerProps))
+
+ if baseLinkerProps.Version_script != nil {
+ versionScript.SetOsArchValueForTarget(os.Name, arch.Name, android.BazelLabelForModuleSrcSingle(ctx, *baseLinkerProps.Version_script))
+ }
+
+ sharedLibs := baseLinkerProps.Shared_libs
+ dynamicDeps.SetOsArchValueForTarget(os.Name, arch.Name, android.BazelLabelForModuleDeps(ctx, sharedLibs))
+ }
}
}
@@ -487,11 +702,20 @@
return relativePaths
}
-// bp2BuildParseExportedIncludes creates a string list attribute contains the
-// exported included directories of a module.
func bp2BuildParseExportedIncludes(ctx android.TopDownMutatorContext, module *Module) bazel.StringListAttribute {
libraryDecorator := module.linker.(*libraryDecorator)
+ return bp2BuildParseExportedIncludesHelper(ctx, module, libraryDecorator)
+}
+func Bp2BuildParseExportedIncludesForPrebuiltLibrary(ctx android.TopDownMutatorContext, module *Module) bazel.StringListAttribute {
+ prebuiltLibraryLinker := module.linker.(*prebuiltLibraryLinker)
+ libraryDecorator := prebuiltLibraryLinker.libraryDecorator
+ return bp2BuildParseExportedIncludesHelper(ctx, module, libraryDecorator)
+}
+
+// bp2BuildParseExportedIncludes creates a string list attribute contains the
+// exported included directories of a module.
+func bp2BuildParseExportedIncludesHelper(ctx android.TopDownMutatorContext, module *Module, libraryDecorator *libraryDecorator) bazel.StringListAttribute {
// Export_system_include_dirs and export_include_dirs are already module dir
// relative, so they don't need to be relativized like include_dirs, which
// are root-relative.
@@ -499,32 +723,38 @@
includeDirs = append(includeDirs, libraryDecorator.flagExporter.Properties.Export_include_dirs...)
includeDirsAttribute := bazel.MakeStringListAttribute(includeDirs)
+ getVariantIncludeDirs := func(includeDirs []string, flagExporterProperties *FlagExporterProperties) []string {
+ variantIncludeDirs := flagExporterProperties.Export_system_include_dirs
+ variantIncludeDirs = append(variantIncludeDirs, flagExporterProperties.Export_include_dirs...)
+
+ // To avoid duplicate includes when base includes + arch includes are combined
+ // TODO: This doesn't take conflicts between arch and os includes into account
+ variantIncludeDirs = bazel.SubtractStrings(variantIncludeDirs, includeDirs)
+ return variantIncludeDirs
+ }
+
for arch, props := range module.GetArchProperties(ctx, &FlagExporterProperties{}) {
if flagExporterProperties, ok := props.(*FlagExporterProperties); ok {
- archIncludeDirs := flagExporterProperties.Export_system_include_dirs
- archIncludeDirs = append(archIncludeDirs, flagExporterProperties.Export_include_dirs...)
-
- // To avoid duplicate includes when base includes + arch includes are combined
- // FIXME: This doesn't take conflicts between arch and os includes into account
- archIncludeDirs = bazel.SubtractStrings(archIncludeDirs, includeDirs)
-
+ archIncludeDirs := getVariantIncludeDirs(includeDirs, flagExporterProperties)
if len(archIncludeDirs) > 0 {
includeDirsAttribute.SetValueForArch(arch.Name, archIncludeDirs)
}
}
}
- for os, props := range module.GetTargetProperties(ctx, &FlagExporterProperties{}) {
- if flagExporterProperties, ok := props.(*FlagExporterProperties); ok {
- osIncludeDirs := flagExporterProperties.Export_system_include_dirs
- osIncludeDirs = append(osIncludeDirs, flagExporterProperties.Export_include_dirs...)
-
- // To avoid duplicate includes when base includes + os includes are combined
- // FIXME: This doesn't take conflicts between arch and os includes into account
- osIncludeDirs = bazel.SubtractStrings(osIncludeDirs, includeDirs)
-
- if len(osIncludeDirs) > 0 {
- includeDirsAttribute.SetValueForOS(os.Name, osIncludeDirs)
+ for os, targetProperties := range module.GetTargetProperties(ctx, &FlagExporterProperties{}) {
+ if flagExporterProperties, ok := targetProperties.Properties.(*FlagExporterProperties); ok {
+ targetIncludeDirs := getVariantIncludeDirs(includeDirs, flagExporterProperties)
+ if len(targetIncludeDirs) > 0 {
+ includeDirsAttribute.SetOsValueForTarget(os.Name, targetIncludeDirs)
+ }
+ }
+ for arch, archProperties := range targetProperties.ArchProperties {
+ if flagExporterProperties, ok := archProperties.(*FlagExporterProperties); ok {
+ targetIncludeDirs := getVariantIncludeDirs(includeDirs, flagExporterProperties)
+ if len(targetIncludeDirs) > 0 {
+ includeDirsAttribute.SetOsArchValueForTarget(os.Name, arch.Name, targetIncludeDirs)
+ }
}
}
}
diff --git a/cc/builder.go b/cc/builder.go
index 51c8a0b..fae9522 100644
--- a/cc/builder.go
+++ b/cc/builder.go
@@ -534,7 +534,7 @@
Implicits: cFlagsDeps,
OrderOnly: pathDeps,
Args: map[string]string{
- "windresCmd": gccCmd(flags.toolchain, "windres"),
+ "windresCmd": mingwCmd(flags.toolchain, "windres"),
"flags": flags.toolchain.WindresFlags(),
},
})
@@ -1069,6 +1069,6 @@
})
}
-func gccCmd(toolchain config.Toolchain, cmd string) string {
+func mingwCmd(toolchain config.Toolchain, cmd string) string {
return filepath.Join(toolchain.GccRoot(), "bin", toolchain.GccTriple()+"-"+cmd)
}
diff --git a/cc/cc.go b/cc/cc.go
index aa218bf..91c4417 100644
--- a/cc/cc.go
+++ b/cc/cc.go
@@ -726,7 +726,6 @@
runtimeDepTag = installDependencyTag{name: "runtime lib"}
testPerSrcDepTag = dependencyTag{name: "test_per_src"}
stubImplDepTag = dependencyTag{name: "stub_impl"}
- llndkStubDepTag = dependencyTag{name: "llndk stub"}
)
func IsSharedDepTag(depTag blueprint.DependencyTag) bool {
@@ -3238,8 +3237,8 @@
return false
}
}
- if depTag == stubImplDepTag || depTag == llndkStubDepTag {
- // We don't track beyond LLNDK or from an implementation library to its stubs.
+ if depTag == stubImplDepTag {
+ // We don't track from an implementation library to its stubs.
return false
}
if depTag == staticVariantTag {
diff --git a/cc/cc_test.go b/cc/cc_test.go
index 5acafbe..7fc044d 100644
--- a/cc/cc_test.go
+++ b/cc/cc_test.go
@@ -2799,12 +2799,8 @@
}
}
expected := []string{
- "android_vendor.29_arm64_armv8-a_shared_1",
- "android_vendor.29_arm64_armv8-a_shared_2",
"android_vendor.29_arm64_armv8-a_shared_current",
"android_vendor.29_arm64_armv8-a_shared",
- "android_vendor.29_arm_armv7-a-neon_shared_1",
- "android_vendor.29_arm_armv7-a-neon_shared_2",
"android_vendor.29_arm_armv7-a-neon_shared_current",
"android_vendor.29_arm_armv7-a-neon_shared",
}
@@ -2813,9 +2809,6 @@
params := result.ModuleForTests("libllndk", "android_vendor.29_arm_armv7-a-neon_shared").Description("generate stub")
android.AssertSame(t, "use VNDK version for default stubs", "current", params.Args["apiLevel"])
- params = result.ModuleForTests("libllndk", "android_vendor.29_arm_armv7-a-neon_shared_1").Description("generate stub")
- android.AssertSame(t, "override apiLevel for versioned stubs", "1", params.Args["apiLevel"])
-
checkExportedIncludeDirs := func(module, variant string, expectedDirs ...string) {
t.Helper()
m := result.ModuleForTests(module, variant).Module()
diff --git a/cc/gen.go b/cc/gen.go
index b152e02..3a1a0e2 100644
--- a/cc/gen.go
+++ b/cc/gen.go
@@ -204,7 +204,7 @@
headerFile := android.GenPathWithExt(ctx, "windmc", srcFile, "h")
rcFile := android.GenPathWithExt(ctx, "windmc", srcFile, "rc")
- windmcCmd := gccCmd(flags.toolchain, "windmc")
+ windmcCmd := mingwCmd(flags.toolchain, "windmc")
ctx.Build(pctx, android.BuildParams{
Rule: windmc,
diff --git a/cc/image.go b/cc/image.go
index 47a424b..c6b209f 100644
--- a/cc/image.go
+++ b/cc/image.go
@@ -579,7 +579,7 @@
// If using a snapshot, the recovery variant under AOSP directories is not needed,
// except for kernel headers, which needs all variants.
- if m.KernelHeadersDecorator() &&
+ if !m.KernelHeadersDecorator() &&
!m.IsSnapshotPrebuilt() &&
usingRecoverySnapshot &&
!isRecoveryProprietaryModule(mctx) {
diff --git a/cc/library.go b/cc/library.go
index 9fb7a24..5e70c51 100644
--- a/cc/library.go
+++ b/cc/library.go
@@ -1813,6 +1813,11 @@
return nil
}
+ if library.hasLLNDKStubs() && ctx.Module().(*Module).UseVndk() {
+ // LLNDK libraries only need a single stubs variant.
+ return []string{android.FutureApiLevel.String()}
+ }
+
// Future API level is implicitly added if there isn't
vers := library.Properties.Stubs.Versions
if inList(android.FutureApiLevel.String(), vers) {
@@ -2154,8 +2159,7 @@
return nil
}
-// versionSelector normalizes the versions in the Stubs.Versions property into MutatedProperties.AllStubsVersions,
-// and propagates the value from implementation libraries to llndk libraries with the same name.
+// versionSelector normalizes the versions in the Stubs.Versions property into MutatedProperties.AllStubsVersions.
func versionSelectorMutator(mctx android.BottomUpMutatorContext) {
if library := moduleLibraryInterface(mctx.Module()); library != nil && CanBeVersionVariant(mctx.Module().(*Module)) {
if library.buildShared() {
@@ -2169,15 +2173,6 @@
// depend on the implementation library and haven't been mutated yet.
library.setAllStubsVersions(versions)
}
-
- if mctx.Module().(*Module).UseVndk() && library.hasLLNDKStubs() {
- // Propagate the version to the llndk stubs module.
- mctx.VisitDirectDepsWithTag(llndkStubDepTag, func(stubs android.Module) {
- if stubsLib := moduleLibraryInterface(stubs); stubsLib != nil {
- stubsLib.setAllStubsVersions(library.allStubsVersions())
- }
- })
- }
}
}
}
diff --git a/cc/object.go b/cc/object.go
index cd71161..39fc43d 100644
--- a/cc/object.go
+++ b/cc/object.go
@@ -157,8 +157,6 @@
// Set arch-specific configurable attributes
compilerAttrs := bp2BuildParseCompilerProps(ctx, m)
- var asFlags bazel.StringListAttribute
-
var deps bazel.LabelListAttribute
for _, props := range m.linker.linkerProps() {
if objectLinkerProps, ok := props.(*ObjectLinkerProperties); ok {
@@ -167,24 +165,6 @@
}
}
- productVariableProps := android.ProductVariableProperties(ctx)
- if props, exists := productVariableProps["Asflags"]; exists {
- // TODO(b/183595873): consider deduplicating handling of product variable properties
- for _, prop := range props {
- flags, ok := prop.Property.([]string)
- if !ok {
- ctx.ModuleErrorf("Could not convert product variable asflag property")
- return
- }
- newFlags, _ := bazel.TryVariableSubstitutions(flags, prop.ProductConfigVariable)
- asFlags.ProductValues = append(asFlags.ProductValues, bazel.ProductVariableValues{
- ProductVariable: prop.ProductConfigVariable,
- Values: newFlags,
- })
- }
- }
- // TODO(b/183595872) warn/error if we're not handling product variables
-
// Don't split cc_object srcs across languages. Doing so would add complexity,
// and this isn't typically done for cc_object.
srcs := compilerAttrs.srcs
@@ -195,7 +175,7 @@
Srcs: srcs,
Deps: deps,
Copts: compilerAttrs.copts,
- Asflags: asFlags,
+ Asflags: compilerAttrs.asFlags,
}
props := bazel.BazelTargetModuleProperties{
diff --git a/cmd/go2bp/Android.bp b/cmd/go2bp/Android.bp
new file mode 100644
index 0000000..53d70b6
--- /dev/null
+++ b/cmd/go2bp/Android.bp
@@ -0,0 +1,26 @@
+// Copyright 2021 Google Inc. All rights reserved.
+//
+// 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 {
+ default_applicable_licenses: ["Android-Apache-2.0"],
+}
+
+blueprint_go_binary {
+ name: "go2bp",
+ deps: [
+ "blueprint-proptools",
+ "bpfix-lib",
+ ],
+ srcs: ["go2bp.go"],
+}
diff --git a/cmd/go2bp/go2bp.go b/cmd/go2bp/go2bp.go
new file mode 100644
index 0000000..67138f1
--- /dev/null
+++ b/cmd/go2bp/go2bp.go
@@ -0,0 +1,361 @@
+// Copyright 2021 Google Inc. All rights reserved.
+//
+// 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 main
+
+import (
+ "bufio"
+ "bytes"
+ "encoding/json"
+ "flag"
+ "fmt"
+ "io/ioutil"
+ "os"
+ "os/exec"
+ "path/filepath"
+ "sort"
+ "strings"
+ "text/template"
+
+ "github.com/google/blueprint/proptools"
+
+ "android/soong/bpfix/bpfix"
+)
+
+type RewriteNames []RewriteName
+type RewriteName struct {
+ prefix string
+ repl string
+}
+
+func (r *RewriteNames) String() string {
+ return ""
+}
+
+func (r *RewriteNames) Set(v string) error {
+ split := strings.SplitN(v, "=", 2)
+ if len(split) != 2 {
+ return fmt.Errorf("Must be in the form of <prefix>=<replace>")
+ }
+ *r = append(*r, RewriteName{
+ prefix: split[0],
+ repl: split[1],
+ })
+ return nil
+}
+
+func (r *RewriteNames) GoToBp(name string) string {
+ ret := name
+ for _, r := range *r {
+ prefix := r.prefix
+ if name == prefix {
+ ret = r.repl
+ break
+ }
+ prefix += "/"
+ if strings.HasPrefix(name, prefix) {
+ ret = r.repl + "-" + strings.TrimPrefix(name, prefix)
+ }
+ }
+ return strings.ReplaceAll(ret, "/", "-")
+}
+
+var rewriteNames = RewriteNames{}
+
+type Exclude map[string]bool
+
+func (e Exclude) String() string {
+ return ""
+}
+
+func (e Exclude) Set(v string) error {
+ e[v] = true
+ return nil
+}
+
+var excludes = make(Exclude)
+var excludeDeps = make(Exclude)
+var excludeSrcs = make(Exclude)
+
+type GoModule struct {
+ Dir string
+}
+
+type GoPackage struct {
+ Dir string
+ ImportPath string
+ Name string
+ Imports []string
+ GoFiles []string
+ TestGoFiles []string
+ TestImports []string
+
+ Module *GoModule
+}
+
+func (g GoPackage) IsCommand() bool {
+ return g.Name == "main"
+}
+
+func (g GoPackage) BpModuleType() string {
+ if g.IsCommand() {
+ return "blueprint_go_binary"
+ }
+ return "bootstrap_go_package"
+}
+
+func (g GoPackage) BpName() string {
+ if g.IsCommand() {
+ return filepath.Base(g.ImportPath)
+ }
+ return rewriteNames.GoToBp(g.ImportPath)
+}
+
+func (g GoPackage) BpDeps(deps []string) []string {
+ var ret []string
+ for _, d := range deps {
+ // Ignore stdlib dependencies
+ if !strings.Contains(d, ".") {
+ continue
+ }
+ if _, ok := excludeDeps[d]; ok {
+ continue
+ }
+ name := rewriteNames.GoToBp(d)
+ ret = append(ret, name)
+ }
+ return ret
+}
+
+func (g GoPackage) BpSrcs(srcs []string) []string {
+ var ret []string
+ prefix, err := filepath.Rel(g.Module.Dir, g.Dir)
+ if err != nil {
+ panic(err)
+ }
+ for _, f := range srcs {
+ f = filepath.Join(prefix, f)
+ if _, ok := excludeSrcs[f]; ok {
+ continue
+ }
+ ret = append(ret, f)
+ }
+ return ret
+}
+
+// AllImports combines Imports and TestImports, as blueprint does not differentiate these.
+func (g GoPackage) AllImports() []string {
+ imports := append([]string(nil), g.Imports...)
+ imports = append(imports, g.TestImports...)
+
+ if len(imports) == 0 {
+ return nil
+ }
+
+ // Sort and de-duplicate
+ sort.Strings(imports)
+ j := 0
+ for i := 1; i < len(imports); i++ {
+ if imports[i] == imports[j] {
+ continue
+ }
+ j++
+ imports[j] = imports[i]
+ }
+ return imports[:j+1]
+}
+
+var bpTemplate = template.Must(template.New("bp").Parse(`
+{{.BpModuleType}} {
+ name: "{{.BpName}}",
+ {{- if not .IsCommand}}
+ pkgPath: "{{.ImportPath}}",
+ {{- end}}
+ {{- if .BpDeps .AllImports}}
+ deps: [
+ {{- range .BpDeps .AllImports}}
+ "{{.}}",
+ {{- end}}
+ ],
+ {{- end}}
+ {{- if .BpSrcs .GoFiles}}
+ srcs: [
+ {{- range .BpSrcs .GoFiles}}
+ "{{.}}",
+ {{- end}}
+ ],
+ {{- end}}
+ {{- if .BpSrcs .TestGoFiles}}
+ testSrcs: [
+ {{- range .BpSrcs .TestGoFiles}}
+ "{{.}}",
+ {{- end}}
+ ],
+ {{- end}}
+}
+`))
+
+func rerunForRegen(filename string) error {
+ buf, err := ioutil.ReadFile(filename)
+ if err != nil {
+ return err
+ }
+
+ scanner := bufio.NewScanner(bytes.NewBuffer(buf))
+
+ // Skip the first line in the file
+ for i := 0; i < 2; i++ {
+ if !scanner.Scan() {
+ if scanner.Err() != nil {
+ return scanner.Err()
+ } else {
+ return fmt.Errorf("unexpected EOF")
+ }
+ }
+ }
+
+ // Extract the old args from the file
+ line := scanner.Text()
+ if strings.HasPrefix(line, "// go2bp ") {
+ line = strings.TrimPrefix(line, "// go2bp ")
+ } else {
+ return fmt.Errorf("unexpected second line: %q", line)
+ }
+ args := strings.Split(line, " ")
+ lastArg := args[len(args)-1]
+ args = args[:len(args)-1]
+
+ // Append all current command line args except -regen <file> to the ones from the file
+ for i := 1; i < len(os.Args); i++ {
+ if os.Args[i] == "-regen" || os.Args[i] == "--regen" {
+ i++
+ } else {
+ args = append(args, os.Args[i])
+ }
+ }
+ args = append(args, lastArg)
+
+ cmd := os.Args[0] + " " + strings.Join(args, " ")
+ // Re-exec pom2bp with the new arguments
+ output, err := exec.Command("/bin/sh", "-c", cmd).Output()
+ if exitErr, _ := err.(*exec.ExitError); exitErr != nil {
+ return fmt.Errorf("failed to run %s\n%s", cmd, string(exitErr.Stderr))
+ } else if err != nil {
+ return err
+ }
+
+ return ioutil.WriteFile(filename, output, 0666)
+}
+
+func main() {
+ flag.Usage = func() {
+ fmt.Fprintf(os.Stderr, `go2bp, a tool to create Android.bp files from go modules
+
+The tool will extract the necessary information from Go files to create an Android.bp that can
+compile them. This needs to be run from the same directory as the go.mod file.
+
+Usage: %s [--rewrite <pkg-prefix>=<replace>] [-exclude <package>] [-regen <file>]
+
+ -rewrite <pkg-prefix>=<replace>
+ rewrite can be used to specify mappings between go package paths and Android.bp modules. The -rewrite
+ option can be specified multiple times. When determining the Android.bp module for a given Go
+ package, mappings are searched in the order they were specified. The first <pkg-prefix> matching
+ either the package directly, or as the prefix '<pkg-prefix>/' will be replaced with <replace>.
+ After all replacements are finished, all '/' characters are replaced with '-'.
+ -exclude <package>
+ Don't put the specified go package in the Android.bp file.
+ -exclude-deps <package>
+ Don't put the specified go package in the dependency lists.
+ -exclude-srcs <module>
+ Don't put the specified source files in srcs or testSrcs lists.
+ -regen <file>
+ Read arguments from <file> and overwrite it.
+
+`, os.Args[0])
+ }
+
+ var regen string
+
+ flag.Var(&excludes, "exclude", "Exclude go package")
+ flag.Var(&excludeDeps, "exclude-dep", "Exclude go package from deps")
+ flag.Var(&excludeSrcs, "exclude-src", "Exclude go file from source lists")
+ flag.Var(&rewriteNames, "rewrite", "Regex(es) to rewrite artifact names")
+ flag.StringVar(®en, "regen", "", "Rewrite specified file")
+ flag.Parse()
+
+ if regen != "" {
+ err := rerunForRegen(regen)
+ if err != nil {
+ fmt.Fprintln(os.Stderr, err)
+ os.Exit(1)
+ }
+ os.Exit(0)
+ }
+
+ if flag.NArg() != 0 {
+ fmt.Fprintf(os.Stderr, "Unused argument detected: %v\n", flag.Args())
+ os.Exit(1)
+ }
+
+ if _, err := os.Stat("go.mod"); err != nil {
+ fmt.Fprintln(os.Stderr, "go.mod file not found")
+ os.Exit(1)
+ }
+
+ cmd := exec.Command("go", "list", "-json", "./...")
+ output, err := cmd.Output()
+ if err != nil {
+ fmt.Fprintf(os.Stderr, "Failed to dump the go packages: %v\n", err)
+ os.Exit(1)
+ }
+ decoder := json.NewDecoder(bytes.NewReader(output))
+
+ pkgs := []GoPackage{}
+ for decoder.More() {
+ pkg := GoPackage{}
+ err := decoder.Decode(&pkg)
+ if err != nil {
+ fmt.Fprintf(os.Stderr, "Failed to parse json: %v\n", err)
+ os.Exit(1)
+ }
+ pkgs = append(pkgs, pkg)
+ }
+
+ buf := &bytes.Buffer{}
+
+ fmt.Fprintln(buf, "// Automatically generated with:")
+ fmt.Fprintln(buf, "// go2bp", strings.Join(proptools.ShellEscapeList(os.Args[1:]), " "))
+
+ for _, pkg := range pkgs {
+ if excludes[pkg.ImportPath] {
+ continue
+ }
+ if len(pkg.BpSrcs(pkg.GoFiles)) == 0 && len(pkg.BpSrcs(pkg.TestGoFiles)) == 0 {
+ continue
+ }
+ err := bpTemplate.Execute(buf, pkg)
+ if err != nil {
+ fmt.Fprintln(os.Stderr, "Error writing", pkg.Name, err)
+ os.Exit(1)
+ }
+ }
+
+ out, err := bpfix.Reformat(buf.String())
+ if err != nil {
+ fmt.Fprintln(os.Stderr, "Error formatting output", err)
+ os.Exit(1)
+ }
+
+ os.Stdout.WriteString(out)
+}
diff --git a/cmd/soong_build/main.go b/cmd/soong_build/main.go
index 7abb67f..0336fb6 100644
--- a/cmd/soong_build/main.go
+++ b/cmd/soong_build/main.go
@@ -17,7 +17,6 @@
import (
"flag"
"fmt"
- "io/fs"
"io/ioutil"
"os"
"path/filepath"
@@ -364,54 +363,41 @@
// - won't be overwritten by corresponding bp2build generated files
//
// And return their paths so they can be left out of the Bazel workspace dir (i.e. ignored)
-func getPathsToIgnoredBuildFiles(topDir string, outDir string, generatedRoot string) ([]string, error) {
+func getPathsToIgnoredBuildFiles(topDir string, generatedRoot string, srcDirBazelFiles []string) []string {
paths := make([]string, 0)
- err := filepath.WalkDir(topDir, func(fFullPath string, fDirEntry fs.DirEntry, err error) error {
+ for _, srcDirBazelFileRelativePath := range srcDirBazelFiles {
+ srcDirBazelFileFullPath := shared.JoinPath(topDir, srcDirBazelFileRelativePath)
+ fileInfo, err := os.Stat(srcDirBazelFileFullPath)
if err != nil {
- // Warn about error, but continue trying to walk the directory tree
- fmt.Fprintf(os.Stderr, "WARNING: Error accessing path '%s', err: %s\n", fFullPath, err)
- return nil
+ // Warn about error, but continue trying to check files
+ fmt.Fprintf(os.Stderr, "WARNING: Error accessing path '%s', err: %s\n", srcDirBazelFileFullPath, err)
+ continue
}
- if fDirEntry.IsDir() {
+ if fileInfo.IsDir() {
// Don't ignore entire directories
- return nil
+ continue
}
- if !(fDirEntry.Name() == "BUILD" || fDirEntry.Name() == "BUILD.bazel") {
+ if !(fileInfo.Name() == "BUILD" || fileInfo.Name() == "BUILD.bazel") {
// Don't ignore this file - it is not a build file
- return nil
+ continue
}
- f := strings.TrimPrefix(fFullPath, topDir+"/")
- if strings.HasPrefix(f, ".repo/") {
- // Don't check for files to ignore in the .repo dir (recursively)
- return fs.SkipDir
- }
- if strings.HasPrefix(f, outDir+"/") {
- // Don't check for files to ignore in the out dir (recursively)
- return fs.SkipDir
- }
- if strings.HasPrefix(f, generatedRoot) {
- // Don't check for files to ignore in the bp2build dir (recursively)
- // NOTE: This is usually under outDir
- return fs.SkipDir
- }
- fDir := filepath.Dir(f)
- if android.ShouldKeepExistingBuildFileForDir(fDir) {
+ srcDirBazelFileDir := filepath.Dir(srcDirBazelFileRelativePath)
+ if android.ShouldKeepExistingBuildFileForDir(srcDirBazelFileDir) {
// Don't ignore this existing build file
- return nil
+ continue
}
- f_bp2build := shared.JoinPath(topDir, generatedRoot, f)
- if _, err := os.Stat(f_bp2build); err == nil {
+ correspondingBp2BuildFile := shared.JoinPath(topDir, generatedRoot, srcDirBazelFileRelativePath)
+ if _, err := os.Stat(correspondingBp2BuildFile); err == nil {
// If bp2build generated an alternate BUILD file, don't exclude this workspace path
// BUILD file clash resolution happens later in the symlink forest creation
- return nil
+ continue
}
- fmt.Fprintf(os.Stderr, "Ignoring existing BUILD file: %s\n", f)
- paths = append(paths, f)
- return nil
- })
+ fmt.Fprintf(os.Stderr, "Ignoring existing BUILD file: %s\n", srcDirBazelFileRelativePath)
+ paths = append(paths, srcDirBazelFileRelativePath)
+ }
- return paths, err
+ return paths
}
// Returns temporary symlink forest excludes necessary for bazel build //external/... (and bazel build //frameworks/...) to work
@@ -431,6 +417,22 @@
return excludes
}
+// Read the bazel.list file that the Soong Finder already dumped earlier (hopefully)
+// It contains the locations of BUILD files, BUILD.bazel files, etc. in the source dir
+func getExistingBazelRelatedFiles(topDir string) ([]string, error) {
+ bazelFinderFile := filepath.Join(filepath.Dir(bootstrap.CmdlineArgs.ModuleListFile), "bazel.list")
+ if !filepath.IsAbs(bazelFinderFile) {
+ // Assume this was a relative path under topDir
+ bazelFinderFile = filepath.Join(topDir, bazelFinderFile)
+ }
+ data, err := ioutil.ReadFile(bazelFinderFile)
+ if err != nil {
+ return nil, err
+ }
+ files := strings.Split(strings.TrimSpace(string(data)), "\n")
+ return files, nil
+}
+
// Run Soong in the bp2build mode. This creates a standalone context that registers
// an alternate pipeline of mutators and singletons specifically for generating
// Bazel BUILD files instead of Ninja files.
@@ -489,14 +491,13 @@
excludes = append(excludes, bootstrap.CmdlineArgs.NinjaBuildDir)
}
- // FIXME: Don't hardcode this here
- topLevelOutDir := "out"
-
- pathsToIgnoredBuildFiles, err := getPathsToIgnoredBuildFiles(topDir, topLevelOutDir, generatedRoot)
+ existingBazelRelatedFiles, err := getExistingBazelRelatedFiles(topDir)
if err != nil {
- fmt.Fprintf(os.Stderr, "Error walking SrcDir: '%s': %s\n", configuration.SrcDir(), err)
+ fmt.Fprintf(os.Stderr, "Error determining existing Bazel-related files: %s\n", err)
os.Exit(1)
}
+
+ pathsToIgnoredBuildFiles := getPathsToIgnoredBuildFiles(topDir, generatedRoot, existingBazelRelatedFiles)
excludes = append(excludes, pathsToIgnoredBuildFiles...)
excludes = append(excludes, getTemporaryExcludes()...)
diff --git a/java/base.go b/java/base.go
index f7989b8..440b004 100644
--- a/java/base.go
+++ b/java/base.go
@@ -1778,3 +1778,9 @@
func (j *Module) ProvidesUsesLib() *string {
return j.usesLibraryProperties.Provides_uses_lib
}
+
+type ModuleWithStem interface {
+ Stem() string
+}
+
+var _ ModuleWithStem = (*Module)(nil)
diff --git a/java/bootclasspath_fragment.go b/java/bootclasspath_fragment.go
index dff8c33..792193f 100644
--- a/java/bootclasspath_fragment.go
+++ b/java/bootclasspath_fragment.go
@@ -502,10 +502,21 @@
global := dexpreopt.GetGlobalConfig(ctx)
+ // Convert content names to their appropriate stems, in case a test library is overriding an actual boot jar
+ var stems []string
+ for _, name := range b.properties.Contents {
+ dep := ctx.GetDirectDepWithTag(name, bootclasspathFragmentContentDepTag)
+ if m, ok := dep.(ModuleWithStem); ok {
+ stems = append(stems, m.Stem())
+ } else {
+ ctx.PropertyErrorf("contents", "%v is not a ModuleWithStem", name)
+ }
+ }
+
// Only create configs for updatable boot jars. Non-updatable boot jars must be part of the
// platform_bootclasspath's classpath proto config to guarantee that they come before any
// updatable jars at runtime.
- return global.UpdatableBootJars.Filter(b.properties.Contents)
+ return global.UpdatableBootJars.Filter(stems)
}
func (b *BootclasspathFragmentModule) getImageConfig(ctx android.EarlyModuleContext) *bootImageConfig {
diff --git a/java/droidstubs.go b/java/droidstubs.go
index 9531056..17c7a7b 100644
--- a/java/droidstubs.go
+++ b/java/droidstubs.go
@@ -51,7 +51,6 @@
lastReleasedApiXmlFile android.WritablePath
privateApiFile android.WritablePath
removedApiFile android.WritablePath
- removedDexApiFile android.WritablePath
nullabilityWarningsFile android.WritablePath
checkCurrentApiTimestamp android.WritablePath
@@ -79,9 +78,6 @@
// the generated removed API filename by Metalava, defaults to <module>_removed.txt
Removed_api_filename *string
- // the generated removed Dex API filename by Metalava.
- Removed_dex_api_filename *string
-
Check_api struct {
Last_released ApiToCheck
@@ -274,11 +270,6 @@
d.removedApiFilePath = android.PathForModuleSrc(ctx, sourceRemovedApiFile)
}
- if String(d.properties.Removed_dex_api_filename) != "" {
- d.removedDexApiFile = android.PathForModuleOut(ctx, "metalava", String(d.properties.Removed_dex_api_filename))
- cmd.FlagWithOutput("--removed-dex-api ", d.removedDexApiFile)
- }
-
if Bool(d.properties.Write_sdk_values) {
d.metadataDir = android.PathForModuleOut(ctx, "metalava", "metadata")
cmd.FlagWithArg("--sdk-values ", d.metadataDir.String())
diff --git a/java/hiddenapi_singleton.go b/java/hiddenapi_singleton.go
index bdf055a..52934a3 100644
--- a/java/hiddenapi_singleton.go
+++ b/java/hiddenapi_singleton.go
@@ -171,7 +171,7 @@
// A platform variant is required but this is for an apex so ignore it.
return false
}
- } else if !apexInfo.InApexVariantByBaseName(requiredApex) {
+ } else if !apexInfo.InApexVariant(requiredApex) {
// An apex variant for a specific apex is required but this is the wrong apex.
return false
}
diff --git a/java/systemserver_classpath_fragment.go b/java/systemserver_classpath_fragment.go
index 80bc0db..7ffb056 100644
--- a/java/systemserver_classpath_fragment.go
+++ b/java/systemserver_classpath_fragment.go
@@ -98,10 +98,21 @@
func (s *SystemServerClasspathModule) ClasspathFragmentToConfiguredJarList(ctx android.ModuleContext) android.ConfiguredJarList {
global := dexpreopt.GetGlobalConfig(ctx)
+ // Convert content names to their appropriate stems, in case a test library is overriding an actual boot jar
+ var stems []string
+ for _, name := range s.properties.Contents {
+ dep := ctx.GetDirectDepWithTag(name, systemServerClasspathFragmentContentDepTag)
+ if m, ok := dep.(ModuleWithStem); ok {
+ stems = append(stems, m.Stem())
+ } else {
+ ctx.PropertyErrorf("contents", "%v is not a ModuleWithStem", name)
+ }
+ }
+
// Only create configs for updatable boot jars. Non-updatable system server jars must be part of the
// platform_systemserverclasspath's classpath proto config to guarantee that they come before any
// updatable jars at runtime.
- return global.UpdatableSystemServerJars.Filter(s.properties.Contents)
+ return global.UpdatableSystemServerJars.Filter(stems)
}
type systemServerClasspathFragmentContentDependencyTag struct {
diff --git a/python/test.go b/python/test.go
index 6713189..7413782 100644
--- a/python/test.go
+++ b/python/test.go
@@ -15,6 +15,8 @@
package python
import (
+ "github.com/google/blueprint/proptools"
+
"android/soong/android"
"android/soong/tradefed"
)
@@ -102,6 +104,9 @@
binary.pythonInstaller = NewPythonInstaller("nativetest", "nativetest64")
test := &testDecorator{binaryDecorator: binary}
+ if hod == android.HostSupportedNoCross && test.testProperties.Test_options.Unit_test == nil {
+ test.testProperties.Test_options.Unit_test = proptools.BoolPtr(true)
+ }
module.bootstrapper = test
module.installer = test
diff --git a/rust/snapshot_utils.go b/rust/snapshot_utils.go
index e0ed1f7..943c790 100644
--- a/rust/snapshot_utils.go
+++ b/rust/snapshot_utils.go
@@ -20,12 +20,12 @@
func (mod *Module) ExcludeFromVendorSnapshot() bool {
// TODO Rust does not yet support snapshotting
- return true
+ return false
}
func (mod *Module) ExcludeFromRecoverySnapshot() bool {
// TODO Rust does not yet support snapshotting
- return true
+ return false
}
func (mod *Module) IsSnapshotLibrary() bool {