My Marlin configs for Fabrikator Mini and CTC i3 Pro B
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

common-features-dependencies.py 5.7KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191
  1. #
  2. # common-features-dependencies.py
  3. # Convenience script to check dependencies and add libs and sources for Marlin Enabled Features
  4. #
  5. import subprocess
  6. import os
  7. import re
  8. try:
  9. import configparser
  10. except ImportError:
  11. import ConfigParser as configparser
  12. from platformio.managers.package import PackageManager
  13. Import("env")
  14. FEATURE_DEPENDENCIES = {}
  15. def load_config():
  16. config = configparser.ConfigParser()
  17. config.read("platformio.ini")
  18. items = config.items('features')
  19. for key in items:
  20. deps = re.sub(',\\s*', '\n', key[1]).strip().split('\n')
  21. if not key[0].upper() in FEATURE_DEPENDENCIES:
  22. FEATURE_DEPENDENCIES[key[0].upper()] = {
  23. 'lib_deps': []
  24. }
  25. for dep in deps:
  26. parts = dep.split('=')
  27. name = parts.pop(0)
  28. rest = '='.join(parts)
  29. if name == 'extra_scripts':
  30. FEATURE_DEPENDENCIES[key[0].upper()]['extra_scripts'] = rest
  31. elif name == 'src_filter':
  32. FEATURE_DEPENDENCIES[key[0].upper()]['src_filter'] = rest
  33. else:
  34. FEATURE_DEPENDENCIES[key[0].upper()]['lib_deps'] += [dep]
  35. def get_all_known_libs():
  36. known_libs = []
  37. for feature in FEATURE_DEPENDENCIES:
  38. if not 'lib_deps' in FEATURE_DEPENDENCIES[feature]:
  39. continue
  40. for dep in FEATURE_DEPENDENCIES[feature]['lib_deps']:
  41. name, _, _ = PackageManager.parse_pkg_uri(dep)
  42. known_libs.append(name)
  43. return known_libs
  44. def get_all_env_libs():
  45. env_libs = []
  46. lib_deps = env.GetProjectOption("lib_deps")
  47. for dep in lib_deps:
  48. name, _, _ = PackageManager.parse_pkg_uri(dep)
  49. env_libs.append(name)
  50. return env_libs
  51. # We need to ignore all non-used libs,
  52. # so if a lib folder lay forgotten in .pio/lib_deps, it
  53. # will not break compiling
  54. def force_ignore_unused_libs():
  55. env_libs = get_all_env_libs()
  56. known_libs = get_all_known_libs()
  57. diff = (list(set(known_libs) - set(env_libs)))
  58. lib_ignore = env.GetProjectOption("lib_ignore") + diff
  59. print("Ignoring libs: ", lib_ignore)
  60. proj = env.GetProjectConfig()
  61. proj.set("env:" + env["PIOENV"], "lib_ignore", lib_ignore)
  62. def install_features_dependencies():
  63. load_config()
  64. for feature in FEATURE_DEPENDENCIES:
  65. if not env.MarlinFeatureIsEnabled(feature):
  66. continue
  67. if 'lib_deps' in FEATURE_DEPENDENCIES[feature]:
  68. print("Adding lib_deps for %s... " % feature)
  69. # deps to add
  70. deps_to_add = {}
  71. for dep in FEATURE_DEPENDENCIES[feature]['lib_deps']:
  72. name, _, _ = PackageManager.parse_pkg_uri(dep)
  73. deps_to_add[name] = dep
  74. # first check if the env already have the dep
  75. deps = env.GetProjectOption("lib_deps")
  76. for dep in deps:
  77. name, _, _ = PackageManager.parse_pkg_uri(dep)
  78. if name in deps_to_add:
  79. del deps_to_add[name]
  80. # check if we need ignore any lib
  81. lib_ignore = env.GetProjectOption("lib_ignore")
  82. for dep in deps:
  83. name, _, _ = PackageManager.parse_pkg_uri(dep)
  84. if name in deps_to_add:
  85. del deps_to_add[name]
  86. # any left?
  87. if len(deps_to_add) <= 0:
  88. continue
  89. # add only the missing deps
  90. proj = env.GetProjectConfig()
  91. proj.set("env:" + env["PIOENV"], "lib_deps", deps + list(deps_to_add.values()))
  92. if 'extra_scripts' in FEATURE_DEPENDENCIES[feature]:
  93. print("Executing extra_scripts for %s... " % feature)
  94. env.SConscript(FEATURE_DEPENDENCIES[feature]['extra_scripts'], exports="env")
  95. if 'src_filter' in FEATURE_DEPENDENCIES[feature]:
  96. print("Adding src_filter for %s... " % feature)
  97. proj = env.GetProjectConfig()
  98. src_filter = env.GetProjectOption("src_filter")
  99. # first we need to remove the references to the same folder
  100. my_srcs = re.findall( r'[+-](<.*?>)', FEATURE_DEPENDENCIES[feature]['src_filter'])
  101. cur_srcs = re.findall( r'[+-](<.*?>)', src_filter[0])
  102. for d in my_srcs:
  103. if d in cur_srcs:
  104. src_filter[0] = re.sub(r'[+-]' + d, '', src_filter[0])
  105. src_filter[0] = FEATURE_DEPENDENCIES[feature]['src_filter'] + ' ' + src_filter[0]
  106. proj.set("env:" + env["PIOENV"], "src_filter", src_filter)
  107. env.Replace(SRC_FILTER=src_filter)
  108. # search the current compiler, considering the OS
  109. def search_compiler():
  110. if env['PLATFORM'] == 'win32':
  111. # the first path have the compiler
  112. compiler_path = None
  113. for path in env['ENV']['PATH'].split(';'):
  114. if re.search(r'platformio\\packages.*\\bin', path):
  115. compiler_path = path
  116. break
  117. if compiler_path == None:
  118. print("Could not find the g++ path")
  119. return None
  120. print(compiler_path)
  121. for file in os.listdir(compiler_path):
  122. if file.endswith("g++.exe"):
  123. return file
  124. print("Could not find the g++")
  125. return None
  126. else:
  127. return env.get('CXX')
  128. # load marlin features
  129. def load_marlin_features():
  130. if "MARLIN_FEATURES" in env:
  131. return
  132. # procces defines
  133. # print(env.Dump())
  134. build_flags = env.get('BUILD_FLAGS')
  135. build_flags = env.ParseFlagsExtended(build_flags)
  136. cxx = search_compiler()
  137. cmd = [cxx]
  138. # build flags from board.json
  139. # if 'BOARD' in env:
  140. # cmd += [env.BoardConfig().get("build.extra_flags")]
  141. for s in build_flags['CPPDEFINES']:
  142. if isinstance(s, tuple):
  143. cmd += ['-D' + s[0] + '=' + str(s[1])]
  144. else:
  145. cmd += ['-D' + s]
  146. # cmd += ['-w -dM -E -x c++ Marlin/src/inc/MarlinConfigPre.h']
  147. cmd += ['-w -dM -E -x c++ buildroot/share/PlatformIO/scripts/common-features-dependencies.h']
  148. cmd = ' '.join(cmd)
  149. print(cmd)
  150. define_list = subprocess.check_output(cmd, shell=True).splitlines()
  151. marlin_features = {}
  152. for define in define_list:
  153. feature = define[8:].strip().decode().split(' ')
  154. feature, definition = feature[0], ' '.join(feature[1:])
  155. marlin_features[feature] = definition
  156. env["MARLIN_FEATURES"] = marlin_features
  157. def MarlinFeatureIsEnabled(env, feature):
  158. load_marlin_features()
  159. return feature in env["MARLIN_FEATURES"]
  160. # add a method for others scripts to check if a feature is enabled
  161. env.AddMethod(MarlinFeatureIsEnabled)
  162. # install all dependencies for features enabled in Configuration.h
  163. install_features_dependencies()
  164. force_ignore_unused_libs()