123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333 |
- // Copyright 2019 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 java
- import (
- "fmt"
- "path/filepath"
- "android/soong/android"
- "android/soong/bazel"
- "github.com/google/blueprint"
- "github.com/google/blueprint/proptools"
- )
- func init() {
- registerPlatformCompatConfigBuildComponents(android.InitRegistrationContext)
- android.RegisterSdkMemberType(CompatConfigSdkMemberType)
- }
- var CompatConfigSdkMemberType = &compatConfigMemberType{
- SdkMemberTypeBase: android.SdkMemberTypeBase{
- PropertyName: "compat_configs",
- SupportsSdk: true,
- },
- }
- func registerPlatformCompatConfigBuildComponents(ctx android.RegistrationContext) {
- ctx.RegisterParallelSingletonType("platform_compat_config_singleton", platformCompatConfigSingletonFactory)
- ctx.RegisterModuleType("platform_compat_config", PlatformCompatConfigFactory)
- ctx.RegisterModuleType("prebuilt_platform_compat_config", prebuiltCompatConfigFactory)
- ctx.RegisterModuleType("global_compat_config", globalCompatConfigFactory)
- }
- var PrepareForTestWithPlatformCompatConfig = android.FixtureRegisterWithContext(registerPlatformCompatConfigBuildComponents)
- func platformCompatConfigPath(ctx android.PathContext) android.OutputPath {
- return android.PathForOutput(ctx, "compat_config", "merged_compat_config.xml")
- }
- type platformCompatConfigProperties struct {
- Src *string `android:"path"`
- }
- type platformCompatConfig struct {
- android.ModuleBase
- android.BazelModuleBase
- properties platformCompatConfigProperties
- installDirPath android.InstallPath
- configFile android.OutputPath
- metadataFile android.OutputPath
- }
- func (p *platformCompatConfig) compatConfigMetadata() android.Path {
- return p.metadataFile
- }
- func (p *platformCompatConfig) CompatConfig() android.OutputPath {
- return p.configFile
- }
- func (p *platformCompatConfig) SubDir() string {
- return "compatconfig"
- }
- type platformCompatConfigMetadataProvider interface {
- compatConfigMetadata() android.Path
- }
- type PlatformCompatConfigIntf interface {
- android.Module
- CompatConfig() android.OutputPath
- // Sub dir under etc dir.
- SubDir() string
- }
- var _ PlatformCompatConfigIntf = (*platformCompatConfig)(nil)
- var _ platformCompatConfigMetadataProvider = (*platformCompatConfig)(nil)
- func (p *platformCompatConfig) GenerateAndroidBuildActions(ctx android.ModuleContext) {
- rule := android.NewRuleBuilder(pctx, ctx)
- configFileName := p.Name() + ".xml"
- metadataFileName := p.Name() + "_meta.xml"
- p.configFile = android.PathForModuleOut(ctx, configFileName).OutputPath
- p.metadataFile = android.PathForModuleOut(ctx, metadataFileName).OutputPath
- path := android.PathForModuleSrc(ctx, String(p.properties.Src))
- rule.Command().
- BuiltTool("process-compat-config").
- FlagWithInput("--jar ", path).
- FlagWithOutput("--device-config ", p.configFile).
- FlagWithOutput("--merged-config ", p.metadataFile)
- p.installDirPath = android.PathForModuleInstall(ctx, "etc", "compatconfig")
- rule.Build(configFileName, "Extract compat/compat_config.xml and install it")
- }
- func (p *platformCompatConfig) AndroidMkEntries() []android.AndroidMkEntries {
- return []android.AndroidMkEntries{android.AndroidMkEntries{
- Class: "ETC",
- OutputFile: android.OptionalPathForPath(p.configFile),
- Include: "$(BUILD_PREBUILT)",
- ExtraEntries: []android.AndroidMkExtraEntriesFunc{
- func(ctx android.AndroidMkExtraEntriesContext, entries *android.AndroidMkEntries) {
- entries.SetString("LOCAL_MODULE_PATH", p.installDirPath.String())
- entries.SetString("LOCAL_INSTALLED_MODULE_STEM", p.configFile.Base())
- },
- },
- }}
- }
- type bazelPlatformCompatConfigAttributes struct {
- Src bazel.LabelAttribute
- }
- func (p *platformCompatConfig) ConvertWithBp2build(ctx android.TopDownMutatorContext) {
- props := bazel.BazelTargetModuleProperties{
- Rule_class: "platform_compat_config",
- Bzl_load_location: "//build/bazel/rules/java:platform_compat_config.bzl",
- }
- attr := &bazelPlatformCompatConfigAttributes{
- Src: *bazel.MakeLabelAttribute(
- android.BazelLabelForModuleSrcSingle(ctx, proptools.String(p.properties.Src)).Label),
- }
- ctx.CreateBazelTargetModule(props, android.CommonAttributes{
- Name: p.Name(),
- }, attr)
- }
- func PlatformCompatConfigFactory() android.Module {
- module := &platformCompatConfig{}
- module.AddProperties(&module.properties)
- android.InitAndroidArchModule(module, android.DeviceSupported, android.MultilibCommon)
- android.InitBazelModule(module)
- return module
- }
- type compatConfigMemberType struct {
- android.SdkMemberTypeBase
- }
- func (b *compatConfigMemberType) AddDependencies(ctx android.SdkDependencyContext, dependencyTag blueprint.DependencyTag, names []string) {
- ctx.AddVariationDependencies(nil, dependencyTag, names...)
- }
- func (b *compatConfigMemberType) IsInstance(module android.Module) bool {
- _, ok := module.(*platformCompatConfig)
- return ok
- }
- func (b *compatConfigMemberType) AddPrebuiltModule(ctx android.SdkMemberContext, member android.SdkMember) android.BpModule {
- return ctx.SnapshotBuilder().AddPrebuiltModule(member, "prebuilt_platform_compat_config")
- }
- func (b *compatConfigMemberType) CreateVariantPropertiesStruct() android.SdkMemberProperties {
- return &compatConfigSdkMemberProperties{}
- }
- type compatConfigSdkMemberProperties struct {
- android.SdkMemberPropertiesBase
- Metadata android.Path
- }
- func (b *compatConfigSdkMemberProperties) PopulateFromVariant(ctx android.SdkMemberContext, variant android.Module) {
- module := variant.(*platformCompatConfig)
- b.Metadata = module.metadataFile
- }
- func (b *compatConfigSdkMemberProperties) AddToPropertySet(ctx android.SdkMemberContext, propertySet android.BpPropertySet) {
- builder := ctx.SnapshotBuilder()
- if b.Metadata != nil {
- snapshotRelativePath := filepath.Join("compat_configs", ctx.Name(), b.Metadata.Base())
- builder.CopyToSnapshot(b.Metadata, snapshotRelativePath)
- propertySet.AddProperty("metadata", snapshotRelativePath)
- }
- }
- var _ android.SdkMemberType = (*compatConfigMemberType)(nil)
- // A prebuilt version of the platform compat config module.
- type prebuiltCompatConfigModule struct {
- android.ModuleBase
- prebuilt android.Prebuilt
- properties prebuiltCompatConfigProperties
- metadataFile android.Path
- }
- type prebuiltCompatConfigProperties struct {
- Metadata *string `android:"path"`
- }
- func (module *prebuiltCompatConfigModule) Prebuilt() *android.Prebuilt {
- return &module.prebuilt
- }
- func (module *prebuiltCompatConfigModule) Name() string {
- return module.prebuilt.Name(module.ModuleBase.Name())
- }
- func (module *prebuiltCompatConfigModule) compatConfigMetadata() android.Path {
- return module.metadataFile
- }
- var _ platformCompatConfigMetadataProvider = (*prebuiltCompatConfigModule)(nil)
- func (module *prebuiltCompatConfigModule) GenerateAndroidBuildActions(ctx android.ModuleContext) {
- module.metadataFile = module.prebuilt.SingleSourcePath(ctx)
- }
- // A prebuilt version of platform_compat_config that provides the metadata.
- func prebuiltCompatConfigFactory() android.Module {
- m := &prebuiltCompatConfigModule{}
- m.AddProperties(&m.properties)
- android.InitSingleSourcePrebuiltModule(m, &m.properties, "Metadata")
- android.InitAndroidArchModule(m, android.DeviceSupported, android.MultilibCommon)
- return m
- }
- // compat singleton rules
- type platformCompatConfigSingleton struct {
- metadata android.Path
- }
- func (p *platformCompatConfigSingleton) GenerateBuildActions(ctx android.SingletonContext) {
- var compatConfigMetadata android.Paths
- ctx.VisitAllModules(func(module android.Module) {
- if !module.Enabled() {
- return
- }
- if c, ok := module.(platformCompatConfigMetadataProvider); ok {
- if !android.IsModulePreferred(module) {
- return
- }
- metadata := c.compatConfigMetadata()
- compatConfigMetadata = append(compatConfigMetadata, metadata)
- }
- })
- if compatConfigMetadata == nil {
- // nothing to do.
- return
- }
- rule := android.NewRuleBuilder(pctx, ctx)
- outputPath := platformCompatConfigPath(ctx)
- rule.Command().
- BuiltTool("process-compat-config").
- FlagForEachInput("--xml ", compatConfigMetadata).
- FlagWithOutput("--merged-config ", outputPath)
- rule.Build("merged-compat-config", "Merge compat config")
- p.metadata = outputPath
- }
- func (p *platformCompatConfigSingleton) MakeVars(ctx android.MakeVarsContext) {
- if p.metadata != nil {
- ctx.Strict("INTERNAL_PLATFORM_MERGED_COMPAT_CONFIG", p.metadata.String())
- }
- }
- func platformCompatConfigSingletonFactory() android.Singleton {
- return &platformCompatConfigSingleton{}
- }
- // ============== merged_compat_config =================
- type globalCompatConfigProperties struct {
- // name of the file into which the metadata will be copied.
- Filename *string
- }
- type globalCompatConfig struct {
- android.ModuleBase
- properties globalCompatConfigProperties
- outputFilePath android.OutputPath
- }
- func (c *globalCompatConfig) GenerateAndroidBuildActions(ctx android.ModuleContext) {
- filename := String(c.properties.Filename)
- inputPath := platformCompatConfigPath(ctx)
- c.outputFilePath = android.PathForModuleOut(ctx, filename).OutputPath
- // This ensures that outputFilePath has the correct name for others to
- // use, as the source file may have a different name.
- ctx.Build(pctx, android.BuildParams{
- Rule: android.Cp,
- Output: c.outputFilePath,
- Input: inputPath,
- })
- }
- func (h *globalCompatConfig) OutputFiles(tag string) (android.Paths, error) {
- switch tag {
- case "":
- return android.Paths{h.outputFilePath}, nil
- default:
- return nil, fmt.Errorf("unsupported module reference tag %q", tag)
- }
- }
- // global_compat_config provides access to the merged compat config xml file generated by the build.
- func globalCompatConfigFactory() android.Module {
- module := &globalCompatConfig{}
- module.AddProperties(&module.properties)
- android.InitAndroidArchModule(module, android.HostAndDeviceSupported, android.MultilibCommon)
- return module
- }
|