| import os |
| import re |
| import meson_impl as impl |
| |
| |
| class Compiler(impl.Compiler): |
| |
| def is_symbol_supported(self, header: str, symbol: str): |
| return super().is_symbol_supported(header, symbol) |
| |
| def is_function_supported(self, function): |
| return super().is_function_supported(function) |
| |
| def is_link_supported(self, name): |
| return super().is_link_supported(name) |
| |
| def has_header_symbol( |
| self, |
| header: str, |
| symbol: str, |
| args=[], |
| dependencies=[], |
| include_directories=[], |
| no_builtin_args=False, |
| prefix=[], |
| required=False, |
| ): |
| # Exclude what is currently not working. |
| result = self.is_symbol_supported(header, symbol) |
| print("has_header_symbol '%s', '%s': %s" % (header, symbol, str(result))) |
| return result |
| |
| def check_header(self, header, prefix=''): |
| result = self.is_header_supported(header) |
| print("check_header '%s': %s" % (header, str(result))) |
| return result |
| |
| def has_function(self, function, args=[], prefix='', dependencies=''): |
| # Exclude what is currently not working. |
| result = self.is_function_supported(function) |
| print("has_function '%s': %s" % (function, str(result))) |
| return result |
| |
| def links(self, snippet, name, args=[], dependencies=[]): |
| # Exclude what is currently not working. |
| result = self.is_link_supported(name) |
| print("links '%s': %s" % (name, str(result))) |
| return result |
| |
| |
| class PkgconfigModule: |
| |
| def generate(self, lib, name='', description='', extra_cflags=[]): |
| return |
| |
| |
| # These globals exposed by the meson API |
| meson = impl.Meson(Compiler()) |
| host_machine = impl.Machine('android') |
| build_machine = impl.Machine('linux') |
| |
| |
| def open_output_file(): |
| impl.open_output_file(r'Android.bp') |
| |
| |
| def close_output_file(): |
| impl.close_output_file() |
| |
| |
| def load_config_file(): |
| impl.load_config_file('python-build/generate_android_build.config') |
| |
| |
| def include_directories(*paths, is_system=False): |
| return impl.IncludeDirectories('', impl.get_include_dirs(paths)) |
| |
| |
| def module_import(name: str): |
| if name == 'python': |
| return impl.PythonModule() |
| if name == 'pkgconfig': |
| return PkgconfigModule() |
| exit('Unhandled module: ' + name) |
| |
| |
| def dependency( |
| *names, |
| required=True, |
| version='', |
| allow_fallback=False, |
| method='', |
| modules=[], |
| optional_modules=[], |
| static=True, |
| fallback=[], |
| include_type='', |
| native=False |
| ): |
| for name in names: |
| if name == 'zlib': |
| return impl.Dependency( |
| name, |
| targets=[ |
| impl.DependencyTarget( |
| 'libz', impl.DependencyTargetType.STATIC_LIBRARY |
| ) |
| ], |
| version=version, |
| found=True, |
| ) |
| |
| if name == 'hardware': |
| return impl.Dependency( |
| name, |
| targets=[ |
| impl.DependencyTarget( |
| 'libhardware', impl.DependencyTargetType.SHARED_LIBRARY |
| ), |
| impl.DependencyTarget( |
| 'hwvulkan_headers', impl.DependencyTargetType.HEADER_LIBRARY |
| ), |
| ], |
| version=version, |
| found=True, |
| ) |
| |
| if name == 'cutils' or name == 'log' or name == 'nativewindow': |
| return impl.Dependency( |
| name, |
| targets=[ |
| impl.DependencyTarget( |
| 'lib' + name, impl.DependencyTargetType.SHARED_LIBRARY |
| ) |
| ], |
| version=version, |
| found=True, |
| ) |
| |
| if name == 'sync': |
| return impl.Dependency( |
| name, |
| targets=[ |
| impl.DependencyTarget( |
| 'lib' + name, impl.DependencyTargetType.STATIC_LIBRARY |
| ) |
| ], |
| version=version, |
| found=True, |
| ) |
| |
| if name == 'android.hardware.graphics.mapper': |
| assert version == '>= 4.0' |
| return impl.Dependency( |
| name, |
| targets=[ |
| impl.DependencyTarget( |
| 'libgralloctypes', impl.DependencyTargetType.STATIC_LIBRARY |
| ), |
| impl.DependencyTarget( |
| '[email protected]', |
| impl.DependencyTargetType.STATIC_LIBRARY, |
| ), |
| impl.DependencyTarget( |
| 'libhidlbase', impl.DependencyTargetType.SHARED_LIBRARY |
| ), |
| impl.DependencyTarget( |
| 'libutils', impl.DependencyTargetType.SHARED_LIBRARY |
| ), |
| ], |
| version=version, |
| found=True, |
| ) |
| |
| return impl.dependency(*names, required=required, version=version) |
| |
| |
| def static_library( |
| target_name, |
| *source_files, |
| c_args=[], |
| cpp_args=[], |
| c_pch='', |
| build_by_default=False, |
| build_rpath='', |
| d_debug=[], |
| d_import_dirs=[], |
| d_module_versions=[], |
| d_unittest=False, |
| dependencies=[], |
| extra_files='', |
| gnu_symbol_visibility='', |
| gui_app=False, |
| implicit_include_directories=False, |
| include_directories=[], |
| install=False, |
| install_dir='', |
| install_mode=[], |
| install_rpath='', |
| install_tag='', |
| link_args=[], |
| link_depends='', |
| link_language='', |
| link_whole=[], |
| link_with=[], |
| name_prefix='', |
| name_suffix='', |
| native=False, |
| objects=[], |
| override_options=[], |
| pic=False, |
| prelink=False, |
| rust_abi='', |
| rust_crate_type='', |
| rust_dependency_map={}, |
| sources='', |
| vala_args=[], |
| win_subsystem='' |
| ): |
| print('static_library: ' + target_name) |
| |
| link_with = impl.get_linear_list(link_with) |
| link_whole = impl.get_linear_list(link_whole) |
| |
| # Emitting link_with/link_whole into a static library isn't useful for building, |
| # shared libraries must specify the whole chain of dependencies. |
| # Leaving them here for traceability though maybe it's less confusing to remove them? |
| _emit_builtin_target( |
| 'cc_library_static', |
| target_name, |
| *source_files, |
| c_args=c_args, |
| cpp_args=cpp_args, |
| dependencies=dependencies, |
| include_directories=include_directories, |
| link_with=link_with, |
| link_whole=link_whole |
| ) |
| |
| return impl.StaticLibrary( |
| target_name, link_with=link_with, link_whole=link_whole |
| ) |
| |
| |
| def _get_sources(input_sources, sources, generated_sources, generated_headers): |
| for source in input_sources: |
| if type(source) is list: |
| _get_sources(source, sources, generated_sources, generated_headers) |
| elif type(source) is impl.CustomTarget: |
| if source.generates_h(): |
| generated_headers.add(source.target_name_h()) |
| if source.generates_c(): |
| generated_sources.add(source.target_name_c()) |
| elif type(source) is impl.CustomTargetItem: |
| source = source.target |
| if source.generates_h(): |
| generated_headers.add(source.target_name_h()) |
| if source.generates_c(): |
| generated_sources.add(source.target_name_c()) |
| elif type(source) is impl.File: |
| sources.add(source.name) |
| elif type(source) is str: |
| sources.add(impl.get_relative_dir(source)) |
| else: |
| exit('source type not handled: ' + str(type(source))) |
| |
| |
| def _emit_builtin_target( |
| builtin_type_name, |
| target_name, |
| *source, |
| c_args=[], |
| cpp_args=[], |
| dependencies=[], |
| include_directories=[], |
| link_with=[], |
| link_whole=[] |
| ): |
| impl.fprint('%s {' % builtin_type_name) |
| impl.fprint(' name: "%s",' % target_name) |
| |
| srcs = set() |
| generated_sources = set() |
| generated_headers = set() |
| for source_arg in source: |
| assert type(source_arg) is list |
| _get_sources(source_arg, srcs, generated_sources, generated_headers) |
| |
| deps = impl.get_set_of_deps(dependencies) |
| include_directories = [impl.get_relative_dir()] + impl.get_include_dirs( |
| include_directories |
| ) |
| static_libs = [] |
| whole_static_libs = [] |
| shared_libs = [] |
| header_libs = [] |
| for dep in deps: |
| print(' dep: ' + dep.name) |
| for src in impl.get_linear_list([dep.sources]): |
| if type(src) == impl.CustomTargetItem: |
| generated_headers.add(src.target.target_name_h()) |
| elif type(src) == impl.CustomTarget: |
| generated_headers.add(src.target_name_h()) |
| else: |
| exit('Unhandled source dependency: ' + str(type(src))) |
| include_directories.extend(impl.get_include_dirs(dep.include_directories)) |
| for target in impl.get_static_libs([dep.link_with]): |
| assert type(target) == impl.StaticLibrary |
| static_libs.append(target.target_name) |
| for target in impl.get_linear_list([dep.link_whole]): |
| assert type(target) == impl.StaticLibrary |
| whole_static_libs.append(target.target_name) |
| for target in dep.targets: |
| if target.target_type == impl.DependencyTargetType.SHARED_LIBRARY: |
| shared_libs.append(target.target_name) |
| elif target.target_type == impl.DependencyTargetType.STATIC_LIBRARY: |
| static_libs.append(target.target_name) |
| elif target.target_type == impl.DependencyTargetType.HEADER_LIBRARY: |
| header_libs.append(target.target_name) |
| |
| for target in impl.get_static_libs(link_with): |
| if type(target) == impl.StaticLibrary: |
| static_libs.append(target.target_name) |
| else: |
| exit('Unhandled link_with type: ' + str(type(target))) |
| |
| for target in impl.get_whole_static_libs(link_whole): |
| if type(target) == impl.StaticLibrary: |
| whole_static_libs.append(target.target_name()) |
| else: |
| exit('Unhandled link_whole type: ' + str(type(target))) |
| |
| # Android turns all warnings into errors but thirdparty projects typically can't handle that |
| cflags = ['-Wno-error'] + impl.get_linear_list( |
| impl.get_project_cflags() + c_args |
| ) |
| cppflags = ['-Wno-error'] + impl.get_linear_list( |
| impl.get_project_cppflags() + cpp_args |
| ) |
| |
| impl.fprint(' srcs: [') |
| for src in srcs: |
| # Filter out header files |
| if not src.endswith('.h'): |
| impl.fprint(' "%s",' % src) |
| impl.fprint(' ],') |
| |
| impl.fprint(' generated_headers: [') |
| for generated in generated_headers: |
| impl.fprint(' "%s",' % generated) |
| impl.fprint(' ],') |
| |
| impl.fprint(' generated_sources: [') |
| for generated in generated_sources: |
| impl.fprint(' "%s",' % generated) |
| impl.fprint(' ],') |
| |
| for arg in impl.get_project_options(): |
| if arg.name == 'c_std': |
| impl.fprint(' c_std: "%s",' % arg.value) |
| elif arg.name == 'cpp_std': |
| impl.fprint(' cpp_std: "%s",' % arg.value) |
| |
| impl.fprint(' conlyflags: [') |
| for arg in cflags: |
| # Escape double quotations |
| arg = re.sub(r'"', '\\"', arg) |
| impl.fprint(' "%s",' % arg) |
| impl.fprint(' ],') |
| impl.fprint(' cppflags: [') |
| for arg in cppflags: |
| # Escape double quotations |
| arg = re.sub(r'"', '\\"', arg) |
| impl.fprint(' "%s",' % arg) |
| impl.fprint(' ],') |
| |
| impl.fprint(' local_include_dirs: [') |
| for inc in include_directories: |
| impl.fprint(' "%s",' % inc) |
| impl.fprint(' ],') |
| |
| impl.fprint(' static_libs: [') |
| for lib in static_libs: |
| impl.fprint(' "%s",' % lib) |
| impl.fprint(' ],') |
| |
| impl.fprint(' whole_static_libs: [') |
| for lib in whole_static_libs: |
| impl.fprint(' "%s",' % lib) |
| impl.fprint(' ],') |
| |
| impl.fprint(' shared_libs: [') |
| for lib in shared_libs: |
| impl.fprint(' "%s",' % lib) |
| impl.fprint(' ],') |
| |
| impl.fprint(' header_libs: [') |
| for lib in header_libs: |
| impl.fprint(' "%s",' % lib) |
| impl.fprint(' ],') |
| |
| impl.fprint('}') |
| |
| |
| def shared_library( |
| target_name, |
| *source, |
| c_args=[], |
| cpp_args=[], |
| c_pch='', |
| build_by_default=False, |
| build_rpath='', |
| d_debug=[], |
| d_import_dirs=[], |
| d_module_versions=[], |
| d_unittest=False, |
| darwin_versions='', |
| dependencies=[], |
| extra_files='', |
| gnu_symbol_visibility='', |
| gui_app=False, |
| implicit_include_directories=False, |
| include_directories=[], |
| install=False, |
| install_dir='', |
| install_mode=[], |
| install_rpath='', |
| install_tag='', |
| link_args=[], |
| link_depends=[], |
| link_language='', |
| link_whole=[], |
| link_with=[], |
| name_prefix='', |
| name_suffix='', |
| native=False, |
| objects=[], |
| override_options=[], |
| rust_abi='', |
| rust_crate_type='', |
| rust_dependency_map={}, |
| sources=[], |
| soversion='', |
| vala_args=[], |
| version='', |
| vs_module_defs='', |
| win_subsystem='' |
| ): |
| print('shared_library: ' + target_name) |
| |
| link_with = impl.get_linear_list([link_with]) |
| link_whole = impl.get_linear_list([link_whole]) |
| |
| _emit_builtin_target( |
| 'cc_library_shared', |
| target_name, |
| *source, |
| c_args=c_args, |
| cpp_args=cpp_args, |
| dependencies=dependencies, |
| include_directories=include_directories, |
| link_with=link_with, |
| link_whole=link_whole |
| ) |
| return impl.SharedLibrary(target_name) |
| |
| |
| def _process_target_name(name): |
| name = re.sub(r'[\[\]]', '', name) |
| return name |
| |
| |
| # Returns string or list of string |
| def _location_wrapper(name_or_list): |
| if isinstance(name_or_list, list): |
| ret = [] |
| for i in name_or_list: |
| ret.append('$(location %s)' % i) |
| return ret |
| |
| assert isinstance(name_or_list, str) |
| return '$(location %s)' % name_or_list |
| |
| |
| def _is_header(name): |
| return re.search(r'\.h[xx|pp]?$', name) != None |
| |
| |
| def _is_source(name): |
| return re.search(r'\.c[c|xx|pp]?$', name) != None |
| |
| |
| def _get_command_args( |
| command, |
| input, |
| output, |
| deps, |
| location_wrap=False, |
| obfuscate_output_c=False, |
| obfuscate_output_h=False, |
| obfuscate_suffix='', |
| ): |
| args = [] |
| for command_item in command[1:]: |
| if isinstance(command_item, list): |
| for item in command_item: |
| assert type(item) == impl.File |
| args.append( |
| _location_wrapper(item.name) if location_wrap else item.name |
| ) |
| continue |
| |
| assert type(command_item) is str |
| match = re.match(r'@INPUT([0-9])?@', command_item) |
| if match != None: |
| if match.group(1) != None: |
| input_index = int(match.group(1)) |
| input_list = impl.get_list_of_relative_inputs(input[input_index]) |
| else: |
| input_list = impl.get_list_of_relative_inputs(input) |
| args.extend( |
| _location_wrapper(input_list) if location_wrap else input_list |
| ) |
| continue |
| |
| match = re.match(r'(.*?)@OUTPUT([0-9])?@', command_item) |
| if match != None: |
| output_list = [] |
| if match.group(2) != None: |
| output_index = int(match.group(2)) |
| selected_output = ( |
| output[output_index] if isinstance(output, list) else output |
| ) |
| output_list.append(impl.get_relative_gen_dir(selected_output)) |
| elif isinstance(output, list): |
| for out in output: |
| output_list.append(impl.get_relative_gen_dir(out)) |
| else: |
| output_list.append(impl.get_relative_gen_dir(output)) |
| for out in output_list: |
| if _is_header(out) and obfuscate_output_h: |
| args.append( |
| match.group(1) + '$(genDir)/%s' % out if location_wrap else out |
| ) |
| else: |
| if _is_source(out) and obfuscate_output_c: |
| out += obfuscate_suffix |
| args.append( |
| match.group(1) + _location_wrapper(out) if location_wrap else out |
| ) |
| continue |
| |
| # Assume used to locate generated outputs |
| match = re.match(r'(.*?)@CURRENT_BUILD_DIR@', command_item) |
| if match != None: |
| args.append('$(genDir)' + '/' + impl.get_relative_dir()) |
| continue |
| |
| # A plain arg |
| if ' ' in command_item: |
| args.append("'%s'" % command_item) |
| else: |
| args.append(command_item) |
| |
| return args |
| |
| |
| # Assume dependencies of custom targets are custom targets that are generating |
| # python scripts; build a python path of their locations. |
| def _get_python_path(deps): |
| python_path = '' |
| for index, dep in enumerate(deps): |
| assert type(dep) == impl.CustomTarget |
| if index > 0: |
| python_path += ':' |
| python_path += '`dirname %s`' % _location_wrapper(':%s' % dep.target_name()) |
| return python_path |
| |
| |
| def _get_export_include_dirs(): |
| dirs = [impl.get_relative_dir()] |
| # HACK for source files that expect that include generated files like: |
| # include "vulkan/runtime/...h" |
| if impl.get_relative_dir().startswith('src'): |
| dirs.append('src') |
| return dirs |
| |
| |
| def _process_wrapped_args_for_python( |
| wrapped_args, python_script, python_script_target_name, deps |
| ): |
| # The python script arg should be replaced with the python binary target name |
| args = impl.replace_wrapped_input_with_target( |
| wrapped_args, python_script, python_script_target_name |
| ) |
| python_path = 'PYTHONPATH=' |
| # Python scripts expect to be able to import other scripts from the same directory, but this |
| # doesn't work in the soong execution environment, so we have to explicitly add the script dir. |
| # We can't use $(location python_binary) because that is missing the relative path; |
| # instead we can use $(location python_script), which happens to work, and we're careful to ensure |
| # the script is in the list of sources even when it's used as the command directly. |
| python_path += '`dirname $(location %s)`' % python_script |
| # Also ensure that scripts generated by dependent custom targets can be imported. |
| if len(deps) > 0: |
| python_path += ':' + _get_python_path(deps) |
| args.insert(0, python_path) |
| return args |
| |
| |
| # Create a custom top level build target |
| # Issues: |
| # - python scripts that call python modules from other directories: |
| # may pass an absolute path to the module directory which violates the sandbox. |
| def custom_target( |
| target_name: str, |
| build_always=False, |
| build_always_stale=False, |
| build_by_default=False, |
| capture=False, |
| command=[], |
| console=False, |
| depend_files=[], |
| depends=[], |
| depfile='', |
| env=[], |
| feed=False, |
| input=[], |
| install=False, |
| install_dir='', |
| install_mode=[], |
| install_tag=[], |
| output=[], |
| ): |
| target_name = _process_target_name(target_name) |
| print('Custom target: ' + target_name) |
| assert type(command) is list |
| program = command[0] |
| program_args = [] |
| |
| # The program can be an array that includes arguments |
| if isinstance(program, list): |
| for arg in program[1:]: |
| assert type(arg) is str |
| program_args.append(arg) |
| program = program[0] |
| |
| assert isinstance(program, impl.Program) |
| assert program.found() |
| |
| args = program_args + _get_command_args(command, input, output, depends) |
| |
| # Python scripts need special handling to find mako library |
| python_script = '' |
| python_script_target_name = '' |
| if program.command.endswith('.py'): |
| python_script = program.command |
| else: |
| for index, arg in enumerate(args): |
| if arg.endswith('.py'): |
| python_script = arg |
| break |
| |
| if python_script != '': |
| python_script_target_name = ( |
| target_name + '_' + os.path.basename(python_script) |
| ) |
| srcs = [python_script] + impl.get_list_of_relative_inputs(depend_files) |
| impl.fprint('python_binary_host {') |
| impl.fprint(' name: "%s",' % python_script_target_name) |
| impl.fprint(' main: "%s",' % python_script) |
| impl.fprint(' srcs: [') |
| for src in srcs: |
| if src.endswith('.py'): |
| impl.fprint(' "%s",' % src) |
| impl.fprint(' ],') |
| impl.fprint(' libs: ["mako"],') |
| # For the PYTHONPATH to work in our genrules command, we need the python interpreter, |
| # not a compiled binary, so disable embedded_launcher. |
| impl.fprint(' version: {') |
| impl.fprint(' py3: {') |
| impl.fprint(' embedded_launcher: false,') |
| impl.fprint(' },') |
| impl.fprint(' },') |
| impl.fprint('}') |
| |
| relative_inputs = impl.get_list_of_relative_inputs(input) |
| # We use python_host_binary instead of calling python scripts directly; |
| # however there's an issue with python locating modules in the same directory |
| # as the script; to workaround that (see _process_wrapped_args_for_python) we |
| # ensure the script is listed in the genrule targets. |
| if python_script != '' and not python_script in relative_inputs: |
| relative_inputs.append(python_script) |
| relative_inputs.extend(impl.get_list_of_relative_inputs(depend_files)) |
| |
| relative_outputs = [] |
| if isinstance(output, list): |
| for file in output: |
| relative_outputs.append(impl.get_relative_gen_dir(file)) |
| else: |
| assert type(output) == str |
| relative_outputs.append(impl.get_relative_gen_dir(output)) |
| |
| # Soong requires genrule to generate only headers OR non-headers |
| generates_h = False |
| generates_c = False |
| for out in relative_outputs: |
| if _is_header(out): |
| generates_h = True |
| if _is_source(out): |
| generates_c = True |
| |
| custom_target = impl.CustomTarget( |
| target_name, relative_outputs, generates_h, generates_c |
| ) |
| |
| program_command = program.command |
| if program_command == 'bison': |
| program_command_arg = 'M4=$(location m4) $(location bison)' |
| elif program_command == 'flex': |
| program_command_arg = 'M4=$(location m4) $(location flex)' |
| elif program_command.endswith('.py'): |
| program_command_arg = _location_wrapper(program_command) |
| else: |
| program_command_arg = program_command |
| |
| program_args = [program_command_arg] + program_args |
| |
| if custom_target.generates_h() and custom_target.generates_c(): |
| # Make a rule for only the headers |
| obfuscate_suffix = '.dummy.h' |
| wrapped_args = program_args + _get_command_args( |
| command, |
| input, |
| output, |
| depends, |
| location_wrap=True, |
| obfuscate_output_c=True, |
| obfuscate_suffix=obfuscate_suffix, |
| ) |
| if python_script: |
| wrapped_args = _process_wrapped_args_for_python( |
| wrapped_args, python_script, python_script_target_name, depends |
| ) |
| |
| command_line = impl.get_command_line_from_args(wrapped_args) |
| if capture: |
| command_line += ' > %s' % _location_wrapper( |
| impl.get_relative_gen_dir(output) |
| ) |
| |
| impl.fprint('genrule {') |
| impl.fprint(' name: "%s",' % custom_target.target_name_h()) |
| impl.fprint(' srcs: [') |
| for src in relative_inputs: |
| impl.fprint(' "%s",' % src) |
| for dep in depends: |
| assert type(dep) is CustomTarget |
| impl.fprint(' ":%s",' % dep.target_name()) |
| impl.fprint(' ],') |
| impl.fprint(' out: [') |
| for out in relative_outputs: |
| if _is_source(out): |
| out += obfuscate_suffix |
| impl.fprint(' "%s",' % out) |
| # The scripts may still write to the assumed .c file, ensure the obfuscated file exists |
| command_line += "; echo '//nothing to see here' > " + _location_wrapper( |
| out |
| ) |
| else: |
| impl.fprint(' "%s",' % out) |
| impl.fprint(' ],') |
| impl.fprint(' tools: [') |
| if python_script_target_name != '': |
| impl.fprint(' "%s",' % python_script_target_name) |
| if program_command == 'bison' or program_command == 'flex': |
| impl.fprint(' "%s",' % 'm4') |
| impl.fprint(' "%s",' % program_command) |
| impl.fprint(' ],') |
| impl.fprint(' export_include_dirs: [') |
| for dir in _get_export_include_dirs(): |
| impl.fprint(' "%s",' % dir) |
| impl.fprint(' ],') |
| impl.fprint(' cmd: "%s"' % command_line) |
| impl.fprint('}') |
| |
| # Make a rule for only the sources |
| obfuscate_suffix = '.dummy.c' |
| wrapped_args = program_args + _get_command_args( |
| command, |
| input, |
| output, |
| depends, |
| location_wrap=True, |
| obfuscate_output_h=True, |
| obfuscate_suffix=obfuscate_suffix, |
| ) |
| if python_script: |
| wrapped_args = _process_wrapped_args_for_python( |
| wrapped_args, python_script, python_script_target_name, depends |
| ) |
| |
| command_line = impl.get_command_line_from_args(wrapped_args) |
| if capture: |
| command_line += ' > %s' % _location_wrapper(get_relative_gen_dir(output)) |
| |
| # We keep the header as an output with an obfuscated name because some scripts insist on having |
| # --out-h (like vk_entrypoints_gen.py). |
| # When Soong depends on this genrule it'll insist on compiling all the outputs, so we replace the |
| # content of all header outputs. |
| impl.fprint('genrule {') |
| impl.fprint(' name: "%s",' % custom_target.target_name_c()) |
| impl.fprint(' srcs: [') |
| for src in relative_inputs: |
| impl.fprint(' "%s",' % src) |
| for dep in depends: |
| assert type(dep) is CustomTarget |
| impl.fprint(' ":%s",' % dep.target_name()) |
| impl.fprint(' ],') |
| impl.fprint(' out: [') |
| for out in relative_outputs: |
| if _is_header(out): |
| out += obfuscate_suffix |
| impl.fprint(' "%s",' % out) |
| # Remove the content because Soong will compile this dummy source file |
| command_line += "; echo '//nothing to see here' > " + _location_wrapper( |
| out |
| ) |
| else: |
| impl.fprint(' "%s",' % out) |
| impl.fprint(' ],') |
| impl.fprint(' tools: [') |
| if python_script_target_name != '': |
| impl.fprint(' "%s",' % python_script_target_name) |
| if program_command == 'bison' or program_command == 'flex': |
| impl.fprint(' "%s",' % 'm4') |
| impl.fprint(' "%s",' % program_command) |
| impl.fprint(' ],') |
| impl.fprint(' cmd: "%s"' % command_line) |
| impl.fprint('}') |
| |
| return custom_target |
| else: |
| wrapped_args = program_args + _get_command_args( |
| command, input, output, depends, location_wrap=True |
| ) |
| if python_script: |
| wrapped_args = _process_wrapped_args_for_python( |
| wrapped_args, python_script, python_script_target_name, depends |
| ) |
| |
| command_line = impl.get_command_line_from_args(wrapped_args) |
| if capture: |
| command_line += ' > %s' % _location_wrapper( |
| impl.get_relative_gen_dir(output) |
| ) |
| |
| impl.fprint('genrule {') |
| impl.fprint(' name: "%s",' % custom_target.target_name()) |
| impl.fprint(' srcs: [') |
| for src in relative_inputs: |
| impl.fprint(' "%s",' % src) |
| for dep in depends: |
| assert type(dep) is impl.CustomTarget |
| impl.fprint(' ":%s",' % dep.target_name()) |
| impl.fprint(' ],') |
| impl.fprint(' out: [') |
| for out in relative_outputs: |
| impl.fprint(' "%s",' % out) |
| impl.fprint(' ],') |
| impl.fprint(' tools: [') |
| if python_script_target_name != '': |
| impl.fprint(' "%s",' % python_script_target_name) |
| if program_command == 'bison' or program_command == 'flex': |
| impl.fprint(' "%s",' % 'm4') |
| impl.fprint(' "%s",' % program_command) |
| impl.fprint(' ],') |
| impl.fprint(' export_include_dirs: [') |
| for dir in _get_export_include_dirs(): |
| impl.fprint(' "%s",' % dir) |
| impl.fprint(' ],') |
| impl.fprint(' cmd: "%s"' % command_line) |
| impl.fprint('}') |
| |
| return custom_target |