Skip to content

Commit

Permalink
Generators can have extra target dependencies. Closes #4131.
Browse files Browse the repository at this point in the history
  • Loading branch information
jpakkane committed May 20, 2019
1 parent 60e1676 commit 79d530e
Show file tree
Hide file tree
Showing 11 changed files with 83 additions and 1 deletion.
3 changes: 3 additions & 0 deletions docs/markdown/Reference-manual.md
Original file line number Diff line number Diff line change
Expand Up @@ -714,6 +714,9 @@ following:

- `arguments` a list of template strings that will be the command line
arguments passed to the executable
- `depends` is an array of build targets that must be built before this
generator can be run. This is used if you have a generator that calls
a second executable that is built in this project. Available since 0.51.0
- `depfile` is a template string pointing to a dependency file that a
generator can write listing all the additional files this target
depends on, for example a C compiler would list all the header files
Expand Down
16 changes: 16 additions & 0 deletions docs/markdown/snippets/gendeps.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
## Generators have a new `depends` keyword argument

Generators can now specify extra dependencies with the `depends`
keyword argument. It matches the behaviour of the same argument in
other functions and specifies that the given targets must be built
before the generator can be run. This is used in cases such as this
one where you need to tell a generator to indirectly invoke a
different program.

```meson
exe = executable(...)
cg = generator(program_runner,
output: ['@BASENAME@.c'],
arguments: ['--use-tool=' + exe.full_path(), '@INPUT@', '@OUTPUT@'],
depends: exe)
```
1 change: 1 addition & 0 deletions mesonbuild/backend/ninjabackend.py
Original file line number Diff line number Diff line change
Expand Up @@ -1800,6 +1800,7 @@ def generate_genlist_for_target(self, genlist, target):
cmd = cmdlist

elem = NinjaBuildElement(self.all_outputs, outfiles, rulename, infilename)
elem.add_dep([self.get_target_filename(x) for x in generator.depends])
if generator.depfile is not None:
elem.add_item('DEPFILE', depfile)
if len(extra_dependencies) > 0:
Expand Down
7 changes: 7 additions & 0 deletions mesonbuild/build.py
Original file line number Diff line number Diff line change
Expand Up @@ -1273,6 +1273,7 @@ def __init__(self, args, kwargs):
self.exe = exe
self.depfile = None
self.capture = False
self.depends = []
self.process_kwargs(kwargs)

def __repr__(self):
Expand Down Expand Up @@ -1321,6 +1322,12 @@ def process_kwargs(self, kwargs):
if not isinstance(capture, bool):
raise InvalidArguments('Capture must be boolean.')
self.capture = capture
if 'depends' in kwargs:
depends = listify(kwargs['depends'], unholder=True)
for d in depends:
if not isinstance(d, BuildTarget):
raise InvalidArguments('Depends entries must be build targets.')
self.depends.append(d)

def get_base_outnames(self, inname):
plainname = os.path.basename(inname)
Expand Down
7 changes: 6 additions & 1 deletion mesonbuild/interpreter.py
Original file line number Diff line number Diff line change
Expand Up @@ -1983,7 +1983,12 @@ def get_cross_property_method(self, args, kwargs):
},
'executable': build.known_exe_kwargs,
'find_program': {'required', 'native'},
'generator': {'arguments', 'output', 'depfile', 'capture', 'preserve_path_from'},
'generator': {'arguments',
'output',
'depends',
'depfile',
'capture',
'preserve_path_from'},
'include_directories': {'is_system'},
'install_data': {'install_dir', 'install_mode', 'rename', 'sources'},
'install_headers': {'install_dir', 'install_mode', 'subdir'},
Expand Down
7 changes: 7 additions & 0 deletions test cases/common/27 pipeline/depends/copyrunner.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
#!/usr/bin/env python3

import sys, subprocess

prog, infile, outfile = sys.argv[1:]

subprocess.check_call([prog, infile, outfile])
22 changes: 22 additions & 0 deletions test cases/common/27 pipeline/depends/filecopier.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#include<stdio.h>
#include<assert.h>

#define BUFSIZE 1024

int main(int argc, char **argv) {
char buffer[BUFSIZE];
size_t num_read;
size_t num_written;
FILE *fin = fopen(argv[1], "rb");
FILE *fout;
assert(fin);
num_read = fread(buffer, 1, BUFSIZE, fin);
assert(num_read > 0);
fclose(fin);
fout = fopen(argv[2], "wb");
assert(fout);
num_written = fwrite(buffer, 1, num_read, fout);
assert(num_written == num_read);
fclose(fout);
return 0;
}
3 changes: 3 additions & 0 deletions test cases/common/27 pipeline/depends/libsrc.c.in
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
int func() {
return 42;
}
11 changes: 11 additions & 0 deletions test cases/common/27 pipeline/depends/meson.build
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
runner = find_program('copyrunner.py')

copier = executable('copier', 'filecopier.c', native: true)

cg = generator(runner,
output: ['@BASENAME@.c'],
arguments: [copier.full_path(), '@INPUT@', '@OUTPUT@'],
depends: copier)

test('generatordep',
executable('gd', 'prog.c', cg.process('libsrc.c.in')))
5 changes: 5 additions & 0 deletions test cases/common/27 pipeline/depends/prog.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
int func();

int main(int argc, char **argv) {
return func() != 42;
}
2 changes: 2 additions & 0 deletions test cases/common/27 pipeline/meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -19,3 +19,5 @@ test('pipelined', e2)
# This is in a subdirectory to make sure
# we write proper subdir paths to output.
subdir('src')

subdir('depends')

0 comments on commit 79d530e

Please sign in to comment.