diff options
-rw-r--r-- | docs/markdown/Reference-manual.md | 3 | ||||
-rw-r--r-- | docs/markdown/Release-notes-for-0.43.0/001-generator-capture.md | 4 | ||||
-rw-r--r-- | mesonbuild/backend/ninjabackend.py | 15 | ||||
-rw-r--r-- | mesonbuild/backend/vs2010backend.py | 10 | ||||
-rw-r--r-- | mesonbuild/build.py | 6 | ||||
-rw-r--r-- | mesonbuild/interpreter.py | 2 | ||||
-rw-r--r-- | test cases/common/98 gen extra/meson.build | 10 | ||||
-rw-r--r-- | test cases/common/98 gen extra/srcgen3.py | 16 |
8 files changed, 64 insertions, 2 deletions
diff --git a/docs/markdown/Reference-manual.md b/docs/markdown/Reference-manual.md index c3636b8..f37fb34 100644 --- a/docs/markdown/Reference-manual.md +++ b/docs/markdown/Reference-manual.md @@ -554,6 +554,9 @@ following: - `output` a template string (or list of template strings) defining how an output file name is (or multiple output names are) generated from a single source file name +- `capture` when this argument is set to true, Meson captures `stdout` + of the `executable` and writes it to the target file specified as + `output`. Available since v0.43.0. The returned object also has methods that are documented in the [object methods section](#generator-object) below. diff --git a/docs/markdown/Release-notes-for-0.43.0/001-generator-capture.md b/docs/markdown/Release-notes-for-0.43.0/001-generator-capture.md new file mode 100644 index 0000000..4eb7fc0 --- /dev/null +++ b/docs/markdown/Release-notes-for-0.43.0/001-generator-capture.md @@ -0,0 +1,4 @@ +## Generator learned capture + +Generators can now be configured to capture the standard output. See +`test cases/common/98 gen extra/meson.build` for an example. diff --git a/mesonbuild/backend/ninjabackend.py b/mesonbuild/backend/ninjabackend.py index d2ba49f..2e6e351 100644 --- a/mesonbuild/backend/ninjabackend.py +++ b/mesonbuild/backend/ninjabackend.py @@ -1814,6 +1814,19 @@ rule FORTRAN_DEP_HACK relout = self.get_target_private_dir(target) args = self.replace_paths(target, args) cmdlist = exe_arr + self.replace_extra_args(args, genlist) + if generator.capture: + exe_data = self.serialize_executable( + cmdlist[0], + cmdlist[1:], + self.environment.get_build_dir(), + capture=outfiles[0] + ) + cmd = self.environment.get_build_command() + ['--internal', 'exe', exe_data] + abs_pdir = os.path.join(self.environment.get_build_dir(), self.get_target_dir(target)) + os.makedirs(abs_pdir, exist_ok=True) + else: + cmd = cmdlist + elem = NinjaBuildElement(self.all_outputs, outfiles, rulename, infilename) if generator.depfile is not None: elem.add_item('DEPFILE', depfile) @@ -1822,7 +1835,7 @@ rule FORTRAN_DEP_HACK elem.add_item('DESC', 'Generating {!r}.'.format(sole_output)) if isinstance(exe, build.BuildTarget): elem.add_dep(self.get_target_filename(exe)) - elem.add_item('COMMAND', cmdlist) + elem.add_item('COMMAND', cmd) elem.write(outfile) def scan_fortran_module_outputs(self, target): diff --git a/mesonbuild/backend/vs2010backend.py b/mesonbuild/backend/vs2010backend.py index cb8dad6..2d18b0e 100644 --- a/mesonbuild/backend/vs2010backend.py +++ b/mesonbuild/backend/vs2010backend.py @@ -128,6 +128,16 @@ class Vs2010Backend(backends.Backend): .replace("@BUILD_ROOT@", self.environment.get_build_dir()) for x in args] cmd = exe_arr + self.replace_extra_args(args, genlist) + if generator.capture: + exe_data = self.serialize_executable( + cmd[0], + cmd[1:], + self.environment.get_build_dir(), + capture=outfiles[0] + ) + cmd = self.environment.get_build_command() + ['--internal', 'exe', exe_data] + abs_pdir = os.path.join(self.environment.get_build_dir(), self.get_target_dir(target)) + os.makedirs(abs_pdir, exist_ok=True) cbs = ET.SubElement(idgroup, 'CustomBuild', Include=infilename) ET.SubElement(cbs, 'Command').text = ' '.join(self.quote_arguments(cmd)) ET.SubElement(cbs, 'Outputs').text = ';'.join(outfiles) diff --git a/mesonbuild/build.py b/mesonbuild/build.py index d3c0b54..8c02d1d 100644 --- a/mesonbuild/build.py +++ b/mesonbuild/build.py @@ -1019,6 +1019,7 @@ class Generator: raise InvalidArguments('First generator argument must be an executable.') self.exe = exe self.depfile = None + self.capture = False self.process_kwargs(kwargs) def __repr__(self): @@ -1062,6 +1063,11 @@ class Generator: if os.path.split(depfile)[1] != depfile: raise InvalidArguments('Depfile must be a plain filename without a subdirectory.') self.depfile = depfile + if 'capture' in kwargs: + capture = kwargs['capture'] + if not isinstance(capture, bool): + raise InvalidArguments('Capture must be boolean.') + self.capture = capture def get_base_outnames(self, inname): plainname = os.path.split(inname)[1] diff --git a/mesonbuild/interpreter.py b/mesonbuild/interpreter.py index 012370d..8197b5e 100644 --- a/mesonbuild/interpreter.py +++ b/mesonbuild/interpreter.py @@ -1335,7 +1335,7 @@ permitted_kwargs = {'add_global_arguments': {'language'}, 'declare_dependency': {'include_directories', 'link_with', 'sources', 'dependencies', 'compile_args', 'link_args', 'version'}, 'executable': exe_kwargs, 'find_program': {'required', 'native'}, - 'generator': {'arguments', 'output', 'depfile'}, + 'generator': {'arguments', 'output', 'depfile', 'capture'}, 'include_directories': {'is_system'}, 'install_data': {'install_dir', 'install_mode', 'sources'}, 'install_headers': {'install_dir', 'subdir'}, diff --git a/test cases/common/98 gen extra/meson.build b/test cases/common/98 gen extra/meson.build index 772f52e..cbbdceb 100644 --- a/test cases/common/98 gen extra/meson.build +++ b/test cases/common/98 gen extra/meson.build @@ -28,3 +28,13 @@ plainname_gen = generator(prog2, plainname_src = plainname_gen.process('name.l') test('plainname', executable('plainname', plainname_src)) + +prog3 = find_program('srcgen3.py') +capture_gen = generator(prog3, + output : ['@BASENAME@.yy.c'], + arguments : ['@INPUT@'], + capture : true) + +capture_src = capture_gen.process('name.l') + +test('capture', executable('capture', capture_src)) diff --git a/test cases/common/98 gen extra/srcgen3.py b/test cases/common/98 gen extra/srcgen3.py new file mode 100644 index 0000000..ad0a5cb --- /dev/null +++ b/test cases/common/98 gen extra/srcgen3.py @@ -0,0 +1,16 @@ +#!/usr/bin/env python3 + +import os +import sys +import argparse + +parser = argparse.ArgumentParser() +parser.add_argument('input', + help='the input file') + +options = parser.parse_args(sys.argv[1:]) + +with open(options.input) as f: + content = f.read().strip() + +print(content) |