5

AOSP now has new build system, and file Android.bp has replaced Android.mk in many places.

Now I want to list source files conditionally depending on platform.

Say something like this:

if(atom)
{
   src: [
      .......list of files.......
   ],
   exclude_srcs: [
      .......list of files.......
   ]
} else
{
   src: [
      .......list of files.......
   ],
   exclude_srcs: [
      .......list of files.......
   ]
}

Any suggestions how to achieve this? Also, how can I achieve logical operations like NOT, OR etc in conditionals?

Thanks in advance.

Vikram Dattu
  • 801
  • 3
  • 8
  • 24

3 Answers3

4

Quote from documentation:

By design, Android.bp files are very simple. There are no conditionals or control flow statements - any complexity is handled in build logic written in Go.

You can read it here.

LLL
  • 1,777
  • 1
  • 15
  • 31
  • 3
    The same document suggests using map to replace conditional statements. The example shows how different sources can be set for arm and x86. – Alex Cohn Jun 21 '17 at 18:58
  • That true, I was more answering to the question in topic than suggesting solution for OP, so thanks for pointing this out. – LLL Jun 22 '17 at 10:50
  • For whose who decide to remove conditionals as recommended, I suggest them to read the following best practices : https://android.googlesource.com/platform/build/soong/+/HEAD/docs/best_practices.md#removing-conditionals – vhamon Jan 31 '22 at 13:52
  • soong_config_module_type seems to be the recommended way but it's only supported from Android 11. – vhamon Feb 01 '22 at 16:06
2

GO

You can write a go script with your conditions. Follow

Is there a way to add/remove module in Android.bp?

What is art.go? And why is it considered a way to write conditionals in bp files?

Conditional compilation

If you just want to include a module conditionally you can define many Android.bp modules and include them based on conditions in Android.mk files. https://android.googlesource.com/platform/build/soong/+/HEAD/docs/best_practices.md#removing-conditionals

soong_config_modules

You will face parsing errors if any of your Android.bp files include libraries not supported by your AOSP.

To fix that you can use soong_config_modules. Note that this is supported only Android 11 R onwards.

Details are given in https://android.googlesource.com/platform/build/soong/+/refs/heads/master/android/soong_config_modules.go

However, I'll give you an example.

Here I am including special libraries when the AOSP is Android 12. Since these libraries might not be present on lower versions, I will not include iot-camera-system.mk in PRODUCT_PACKAGES so it will not be included as a preinstalled app.

What specifically I will achieve with soong_config_modules is removal of parsing errors when these libraries are not present (Android parses all Android.bp files to form a parse tree, it also checks for the existence of their dependencies and build fails when they are not present).

iot-camera-system.mk

# CameraApp Android Application Package

ifeq ($(PLATFORM_VERSION), $(filter $(PLATFORM_VERSION),S 12))
  PRODUCT_PACKAGES += CameraApp
  SOONG_CONFIG_NAMESPACES += camera
  SOONG_CONFIG_camera += camtargets
  SOONG_CONFIG_camera_camtargets := newCameraTarget
else
  SOONG_CONFIG_NAMESPACES += camera
  SOONG_CONFIG_camera += camtargets
  SOONG_CONFIG_camera_camtargets := oldCameraTarget
endif

Android.bp

// This introduces the module type camera_cc_defaults
// If target.mk file contained:
//
// SOONG_CONFIG_NAMESPACES += camera
// SOONG_CONFIG_camera += camtargets
// SOONG_CONFIG_camera_camtargets := newCameraTarget
//
// Then our libs would build with static_libs

soong_config_module_type {
    name: "camera_cc_defaults",
    module_type: "cc_defaults",
    config_namespace: "camera",
    variables: ["camtargets"],
    properties: ["static_libs"],
}

soong_config_string_variable {
    name: "camtargets",
    values: ["oldCameraTarget", "newCameraTarget"],
}

camera_cc_defaults {
    name: "camera_defaults",
    soong_config_variables: {
        camtargets: {
            oldCameraTarget: {
                static_libs: [
                ],
            },
            newCameraTarget: {
                static_libs: [
                    "androidx.core_core-ktx",
                    "androidx.fragment_fragment-ktx",
                    "androidx.navigation_navigation-fragment-ktx",
                    "androidx.navigation_navigation-ui-ktx",
                    "androidx.lifecycle_lifecycle-runtime-ktx",
                    "kotlinx_coroutines",
                    "kotlinx_coroutines_android",
                ],
            },
        },
    },
}

android_library {
  name: "utils",
  defaults: ["camera_defaults"],
  manifest: "utils/src/main/AndroidManifest.xml",
  platform_apis: true,

  srcs: [
    "utils/src/main/java/com/example/android/camera/utils/*.kt",
  ],

  resource_dirs: [
    "utils/src/main/res/",
  ],

  static_libs: [
    "androidx-constraintlayout_constraintlayout",
    "androidx.appcompat_appcompat",
    "androidx.localbroadcastmanager_localbroadcastmanager",
    "com.google.android.material_material",
    "androidx.exifinterface_exifinterface",
    "androidx.core_core",
    "androidx.preference_preference",
    "androidx.fragment_fragment",
    "androidx.recyclerview_recyclerview",
    "androidx.lifecycle_lifecycle-runtime",
    "androidx.lifecycle_lifecycle-extensions",
    "kotlin-stdlib",
    "kotlin-reflect",
    "gson-prebuilt-jar",
  ],

  optimize: {
    enabled: false,
  },
  dex_preopt: {
    enabled: false,
  },
}

android_app {
  name: "CameraApp",
  defaults: ["camera_defaults"],
  manifest: "app/src/main/AndroidManifest.xml",
  privileged: true,
  platform_apis: true,
  certificate: "platform",

  srcs: [
    "app/src/main/java/com/example/android/camera2/video/*.kt",
    "app/src/main/java/com/example/android/camera2/video/fragments/*.kt",
    "app/src/main/java/com/example/android/camera2/video/overlay/*.kt",
  ],

  resource_dirs: [
    "app/src/main/res/",
  ],

  static_libs: [
    "androidx-constraintlayout_constraintlayout",
    "androidx.appcompat_appcompat",
    "androidx.localbroadcastmanager_localbroadcastmanager",
    "com.google.android.material_material",
    "androidx.exifinterface_exifinterface",
    "androidx.core_core",
    "androidx.preference_preference",
    "androidx.fragment_fragment",
    "androidx.recyclerview_recyclerview",
    "androidx.lifecycle_lifecycle-runtime",
    "androidx.lifecycle_lifecycle-extensions",
    "kotlin-stdlib",
    "kotlin-reflect",
    "gson-prebuilt-jar",
    "utils",
  ],

  optimize: {
    enabled: false,
  },
  dex_preopt: {
    enabled: false,
  },
}
zeitgeist
  • 852
  • 12
  • 19
1

this a sample on how to add a conditional in a bp file:

cc_library {  
    ...  
    srcs: ["generic.cpp"],  
    arch: {  
        arm: {  
            srcs: ["arm.cpp"],  
        },  
        x86: {  
            srcs: ["x86.cpp"],  
        },  
    },  
}  
Smog
  • 625
  • 6
  • 19
Cesar Leon
  • 19
  • 2
  • So, you're using some of the builtin logic to select stuff based on architecture. Not an answer to the general question regarding how to manage conditionals, though. – Dustin Oprea Jan 13 '20 at 21:10