fbt_apps.py 2.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. from SCons.Builder import Builder
  2. from SCons.Action import Action
  3. from SCons.Warnings import warn, WarningOnByDefault
  4. from ansi.color import fg
  5. from fbt.appmanifest import (
  6. FlipperAppType,
  7. AppManager,
  8. ApplicationsCGenerator,
  9. FlipperManifestException,
  10. )
  11. # Adding objects for application management to env
  12. # AppManager env["APPMGR"] - loads all manifests; manages list of known apps
  13. # AppBuildset env["APPBUILD"] - contains subset of apps, filtered for current config
  14. def LoadAppManifest(env, entry):
  15. try:
  16. APP_MANIFEST_NAME = "application.fam"
  17. manifest_glob = entry.glob(APP_MANIFEST_NAME)
  18. if len(manifest_glob) == 0:
  19. raise FlipperManifestException(
  20. f"Folder {entry}: manifest {APP_MANIFEST_NAME} is missing"
  21. )
  22. app_manifest_file_path = manifest_glob[0].rfile().abspath
  23. env["APPMGR"].load_manifest(app_manifest_file_path, entry)
  24. env.Append(PY_LINT_SOURCES=[app_manifest_file_path])
  25. except FlipperManifestException as e:
  26. warn(WarningOnByDefault, str(e))
  27. def PrepareApplicationsBuild(env):
  28. appbuild = env["APPBUILD"] = env["APPMGR"].filter_apps(
  29. env["APPS"], env.subst("f${TARGET_HW}")
  30. )
  31. env.Append(
  32. SDK_HEADERS=appbuild.get_sdk_headers(),
  33. )
  34. def DumpApplicationConfig(target, source, env):
  35. print(f"Loaded {len(env['APPMGR'].known_apps)} app definitions.")
  36. print(fg.boldgreen("Firmware modules configuration:"))
  37. for apptype in FlipperAppType:
  38. app_sublist = env["APPBUILD"].get_apps_of_type(apptype)
  39. if app_sublist:
  40. print(
  41. fg.green(f"{apptype.value}:\n\t"),
  42. ", ".join(app.appid for app in app_sublist),
  43. )
  44. def build_apps_c(target, source, env):
  45. target_file_name = target[0].path
  46. gen = ApplicationsCGenerator(env["APPBUILD"], env.subst("$LOADER_AUTOSTART"))
  47. with open(target_file_name, "w") as file:
  48. file.write(gen.generate())
  49. def generate(env):
  50. env.AddMethod(LoadAppManifest)
  51. env.AddMethod(PrepareApplicationsBuild)
  52. env.SetDefault(
  53. APPMGR=AppManager(),
  54. APPBUILD_DUMP=env.Action(
  55. DumpApplicationConfig,
  56. "\tINFO\t",
  57. ),
  58. )
  59. env.Append(
  60. BUILDERS={
  61. "ApplicationsC": Builder(
  62. action=Action(
  63. build_apps_c,
  64. "${APPSCOMSTR}",
  65. ),
  66. suffix=".c",
  67. ),
  68. }
  69. )
  70. def exists(env):
  71. return True