aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--mesonbuild/backend/backends.py13
-rw-r--r--mesonbuild/compilers.py11
-rw-r--r--mesonbuild/environment.py11
-rw-r--r--mesonbuild/interpreter.py26
-rwxr-xr-xmesonbuild/scripts/gtkdochelper.py9
-rw-r--r--test cases/common/121 interpreter copy mutable var on assignment/meson.build20
-rw-r--r--test cases/common/37 has header/meson.build20
-rw-r--r--test cases/common/48 test args/env2vars.c23
-rw-r--r--test cases/common/48 test args/meson.build7
-rw-r--r--test cases/frameworks/7 gnome/gir/meson.build2
-rw-r--r--test cases/frameworks/7 gnome/installed_files.txt2
-rw-r--r--test cases/vala/6 static library/installed_files.txt1
-rw-r--r--test cases/vala/6 static library/meson.build6
13 files changed, 127 insertions, 24 deletions
diff --git a/mesonbuild/backend/backends.py b/mesonbuild/backend/backends.py
index 2861bb6..45d946f 100644
--- a/mesonbuild/backend/backends.py
+++ b/mesonbuild/backend/backends.py
@@ -271,6 +271,9 @@ class Backend():
def object_filename_from_source(self, target, source):
if isinstance(source, mesonlib.File):
source = source.fname
+ # foo.vala files compile down to foo.c and then foo.c.o, not foo.vala.o
+ if source.endswith('.vala'):
+ source = os.path.join(self.get_target_private_dir(target), source[:-5] + '.c')
return source.replace('/', '_').replace('\\', '_') + '.' + self.environment.get_object_suffix()
def determine_ext_objs(self, extobj, proj_dir_to_build_root):
@@ -598,11 +601,17 @@ class Backend():
i = i.replace('@OUTDIR@', outdir)
elif '@DEPFILE@' in i:
if target.depfile is None:
- raise MesonException('Custom target %s has @DEPFILE@ but no depfile keyword argument.' % target.name)
+ msg = 'Custom target {!r} has @DEPFILE@ but no depfile ' \
+ 'keyword argument.'.format(target.name)
+ raise MesonException(msg)
dfilename = os.path.join(outdir, target.depfile)
i = i.replace('@DEPFILE@', dfilename)
elif '@PRIVATE_OUTDIR_' in i:
- match = re.search('@PRIVATE_OUTDIR_(ABS_)?([-a-zA-Z0-9.@:]*)@', i)
+ match = re.search('@PRIVATE_OUTDIR_(ABS_)?([^\/\s*]*)@', i)
+ if not match:
+ msg = 'Custom target {!r} has an invalid argument {!r}' \
+ ''.format(target.name, i)
+ raise MesonException(msg)
source = match.group(0)
if match.group(1) is None and not absolute_paths:
lead_dir = ''
diff --git a/mesonbuild/compilers.py b/mesonbuild/compilers.py
index bbe6a72..9b76f29 100644
--- a/mesonbuild/compilers.py
+++ b/mesonbuild/compilers.py
@@ -638,13 +638,11 @@ class CCompiler(Compiler):
code = 'int main(int argc, char **argv) { int class=0; return class; }\n'
return self.sanity_check_impl(work_dir, environment, 'sanitycheckc.c', code)
- def has_header(self, hname, env, extra_args=None, dependencies=None):
+ def has_header(self, hname, prefix, env, extra_args=None, dependencies=None):
if extra_args is None:
extra_args = []
- templ = '''#include<%s>
-int someSymbolHereJustForFun;
-'''
- return self.compiles(templ % hname, env, extra_args, dependencies)
+ code = '{}\n#include<{}>\nint someUselessSymbol;'.format(prefix, hname)
+ return self.compiles(code, env, extra_args, dependencies)
def has_header_symbol(self, hname, symbol, prefix, env, extra_args=None, dependencies=None):
if extra_args is None:
@@ -1854,6 +1852,9 @@ class VisualStudioCCompiler(CCompiler):
result.append(i)
return result
+ def get_werror_args(self):
+ return ['/WX']
+
def get_include_args(self, path, is_system):
if path == '':
path = '.'
diff --git a/mesonbuild/environment.py b/mesonbuild/environment.py
index f7045f4..405685c 100644
--- a/mesonbuild/environment.py
+++ b/mesonbuild/environment.py
@@ -331,6 +331,13 @@ class Environment():
if len(rest) == 2:
defines[rest[0]] = rest[1]
return defines
+ @staticmethod
+ def get_gnu_version_from_defines(defines):
+ dot = '.'
+ major = defines.get('__GNUC__', '0')
+ minor = defines.get('__GNUC_MINOR__', '0')
+ patch = defines.get('__GNUC_PATCHLEVEL__', '0')
+ return dot.join((major, minor, patch))
@staticmethod
def get_gnu_compiler_type(defines):
@@ -385,6 +392,7 @@ class Environment():
popen_exceptions[compiler] = 'no pre-processor defines'
continue
gtype = self.get_gnu_compiler_type(defines)
+ version = self.get_gnu_version_from_defines(defines)
return GnuCCompiler(ccache + [compiler], version, gtype, is_cross, exe_wrap, defines)
if 'clang' in out:
if 'Apple' in out:
@@ -443,6 +451,7 @@ class Environment():
popen_exceptions[compiler] = 'no pre-processor defines'
continue
gtype = self.get_gnu_compiler_type(defines)
+ version = self.get_gnu_version_from_defines(defines)
return GnuFortranCompiler([compiler], version, gtype, is_cross, exe_wrap, defines)
if 'G95' in out:
@@ -524,6 +533,7 @@ class Environment():
popen_exceptions[compiler] = 'no pre-processor defines'
continue
gtype = self.get_gnu_compiler_type(defines)
+ version = self.get_gnu_version_from_defines(defines)
return GnuCPPCompiler(ccache + [compiler], version, gtype, is_cross, exe_wrap, defines)
if 'clang' in out:
if 'Apple' in out:
@@ -563,6 +573,7 @@ class Environment():
version = search_version(out)
if 'Free Software Foundation' in out:
defines = self.get_gnu_compiler_defines(exelist)
+ version = self.get_gnu_version_from_defines(defines)
return GnuObjCCompiler(exelist, version, is_cross, exe_wrap, defines)
if out.startswith('Apple LLVM'):
return ClangObjCCompiler(exelist, version, CLANG_OSX, is_cross, exe_wrap)
diff --git a/mesonbuild/interpreter.py b/mesonbuild/interpreter.py
index 0030660..33587a4 100644
--- a/mesonbuild/interpreter.py
+++ b/mesonbuild/interpreter.py
@@ -92,6 +92,10 @@ class InterpreterObject():
return self.methods[method_name](args, kwargs)
raise InvalidCode('Unknown method "%s" in object.' % method_name)
+class MutableInterpreterObject(InterpreterObject):
+ def __init__(self):
+ super().__init__()
+
class TryRunResultHolder(InterpreterObject):
def __init__(self, res):
super().__init__()
@@ -182,14 +186,13 @@ class ConfigureFileHolder(InterpreterObject):
self.held_object = build.ConfigureFile(subdir, sourcename, targetname, configuration_data)
-class EnvironmentVariablesHolder(InterpreterObject):
+class EnvironmentVariablesHolder(MutableInterpreterObject):
def __init__(self):
super().__init__()
self.held_object = build.EnvironmentVariables()
self.methods.update({'set': self.set_method,
'append': self.append_method,
'prepend' : self.prepend_method,
- 'copy' : self.copy_method,
})
@stringArgs
@@ -212,11 +215,8 @@ class EnvironmentVariablesHolder(InterpreterObject):
def prepend_method(self, args, kwargs):
self.add_var(self.held_object.prepend, args, kwargs)
- def copy_method(self, args, kwargs):
- return copy.deepcopy(self)
-
-class ConfigurationDataHolder(InterpreterObject):
+class ConfigurationDataHolder(MutableInterpreterObject):
def __init__(self):
super().__init__()
self.used = False # These objects become immutable after use in configure_file.
@@ -896,15 +896,18 @@ class CompilerHolder(InterpreterObject):
if len(args) != 1:
raise InterpreterException('has_header method takes exactly one argument.')
check_stringlist(args)
- string = args[0]
+ hname = args[0]
+ prefix = kwargs.get('prefix', '')
+ if not isinstance(prefix, str):
+ raise InterpreterException('Prefix argument of has_header must be a string.')
extra_args = self.determine_args(kwargs)
deps = self.determine_dependencies(kwargs, allowed_dep_types=(dependencies.Dependency,))
- haz = self.compiler.has_header(string, self.environment, extra_args, deps)
+ haz = self.compiler.has_header(hname, prefix, self.environment, extra_args, deps)
if haz:
h = mlog.green('YES')
else:
h = mlog.red('NO')
- mlog.log('Has header "%s":' % string, h)
+ mlog.log('Has header "%s":' % hname, h)
return haz
def has_header_symbol_method(self, args, kwargs):
@@ -915,7 +918,7 @@ class CompilerHolder(InterpreterObject):
symbol = args[1]
prefix = kwargs.get('prefix', '')
if not isinstance(prefix, str):
- raise InterpreterException('Prefix argument of has_function must be a string.')
+ raise InterpreterException('Prefix argument of has_header_symbol must be a string.')
extra_args = self.determine_args(kwargs)
deps = self.determine_dependencies(kwargs, allowed_dep_types=(dependencies.Dependency,))
haz = self.compiler.has_header_symbol(hname, symbol, prefix, self.environment, extra_args, deps)
@@ -2461,6 +2464,9 @@ requirements use the version keyword argument instead.''')
value = self.to_native(value)
if not self.is_assignable(value):
raise InvalidCode('Tried to assign an invalid value to variable.')
+ # For mutable objects we need to make a copy on assignment
+ if isinstance(value, MutableInterpreterObject):
+ value = copy.deepcopy(value)
self.set_variable(var_name, value)
return value
diff --git a/mesonbuild/scripts/gtkdochelper.py b/mesonbuild/scripts/gtkdochelper.py
index 220801d..e34b541 100755
--- a/mesonbuild/scripts/gtkdochelper.py
+++ b/mesonbuild/scripts/gtkdochelper.py
@@ -90,10 +90,11 @@ def build_gtkdoc(source_root, build_root, doc_subdir, src_subdir,
f_abs = os.path.join(doc_src, f)
shutil.copyfile(f_abs, os.path.join(htmldir, os.path.basename(f_abs)))
- scan_cmd = ['gtkdoc-scan',
- '--module=' + module,
- '--source-dir=' + abs_src,
- '--ignore-headers=' + ignore_headers] + scan_args
+ scan_cmd = ['gtkdoc-scan', '--module=' + module, '--source-dir=' + abs_src]
+ if ignore_headers:
+ scan_cmd.append('--ignore-headers=' + ' '.join(ignore_headers))
+ # Add user-specified arguments
+ scan_cmd += scan_args
gtkdoc_run_check(scan_cmd, abs_out)
if gobject_typesfile:
diff --git a/test cases/common/121 interpreter copy mutable var on assignment/meson.build b/test cases/common/121 interpreter copy mutable var on assignment/meson.build
new file mode 100644
index 0000000..8b15357
--- /dev/null
+++ b/test cases/common/121 interpreter copy mutable var on assignment/meson.build
@@ -0,0 +1,20 @@
+project('foo', 'c')
+
+a = configuration_data()
+a.set('HELLO', 1)
+
+b = a
+
+assert(a.has('HELLO'), 'Original config data should be set on a')
+assert(b.has('HELLO'), 'Original config data should be set on copy')
+
+configure_file(output : 'b.h', configuration : b)
+
+# This should still work, as we didn't use the original above but a copy!
+a.set('WORLD', 1)
+
+assert(a.has('WORLD'), 'New config data should have been set')
+assert(not b.has('WORLD'), 'New config data set should not affect var copied earlier')
+
+configure_file(output : 'a.h', configuration : a)
+
diff --git a/test cases/common/37 has header/meson.build b/test cases/common/37 has header/meson.build
index ce6e71a..4f9b94f 100644
--- a/test cases/common/37 has header/meson.build
+++ b/test cases/common/37 has header/meson.build
@@ -1,10 +1,28 @@
project('has header', 'c', 'cpp')
foreach comp : [meson.get_compiler('c'), meson.get_compiler('cpp')]
- if comp.has_header('stdio.h') == false
+ if not comp.has_header('stdio.h')
error('Stdio missing.')
endif
+ # stdio.h doesn't actually need stdlib.h, but I don't know any headers on
+ # UNIX/Linux that need other headers defined beforehand
+ if not comp.has_header('stdio.h', prefix : '#include <stdlib.h>')
+ error('Stdio missing.')
+ endif
+
+ # XInput.h needs windows.h included beforehand. We only do this check on MSVC
+ # because MinGW often defines its own wrappers that pre-include windows.h
+ if comp.get_id() == 'msvc'
+ if not comp.has_header('XInput.h', prefix : '#include <windows.h>')
+ error('XInput.h is missing on Windows')
+ endif
+ if comp.has_header('XInput.h')
+ error('XInput.h needs windows.h')
+ endif
+ endif
+
+
if comp.has_header('ouagadougou.h')
error('Found non-existant header.')
endif
diff --git a/test cases/common/48 test args/env2vars.c b/test cases/common/48 test args/env2vars.c
new file mode 100644
index 0000000..19250a8
--- /dev/null
+++ b/test cases/common/48 test args/env2vars.c
@@ -0,0 +1,23 @@
+#include<stdio.h>
+#include<string.h>
+#include<stdlib.h>
+
+int main(int argc, char **argv) {
+ if(strcmp(getenv("first"), "something-else") != 0) {
+ fprintf(stderr, "First envvar is wrong. %s\n", getenv("first"));
+ return 1;
+ }
+ if(strcmp(getenv("second"), "val2") != 0) {
+ fprintf(stderr, "Second envvar is wrong.\n");
+ return 1;
+ }
+ if(strcmp(getenv("third"), "val3:and_more") != 0) {
+ fprintf(stderr, "Third envvar is wrong.\n");
+ return 1;
+ }
+ if(strstr(getenv("PATH"), "fakepath:") != NULL) {
+ fprintf(stderr, "Third envvar is wrong.\n");
+ return 1;
+ }
+ return 0;
+}
diff --git a/test cases/common/48 test args/meson.build b/test cases/common/48 test args/meson.build
index 6400198..f599bf7 100644
--- a/test cases/common/48 test args/meson.build
+++ b/test cases/common/48 test args/meson.build
@@ -2,6 +2,7 @@ project('test features', 'c')
e1 = executable('cmd_args', 'cmd_args.c')
e2 = executable('envvars', 'envvars.c')
+e3 = executable('env2vars', 'env2vars.c')
env = environment()
env.set('first', 'val1')
@@ -9,6 +10,12 @@ env.set('second', 'val2')
env.set('third', 'val3', 'and_more', separator: ':')
env.append('PATH', 'fakepath', separator: ':')
+# Make sure environment objects are copied on assignment and we can
+# change the copy without affecting the original environment object.
+env2 = env
+env2.set('first', 'something-else')
+
test('command line arguments', e1, args : ['first', 'second'])
test('environment variables', e2, env : env)
+test('environment variables 2', e3, env : env2)
test('file arg', find_program('tester.py'), args : files('testfile.txt'))
diff --git a/test cases/frameworks/7 gnome/gir/meson.build b/test cases/frameworks/7 gnome/gir/meson.build
index a513062..51bbbab 100644
--- a/test cases/frameworks/7 gnome/gir/meson.build
+++ b/test cases/frameworks/7 gnome/gir/meson.build
@@ -1,7 +1,7 @@
libsources = ['meson-sample.c', 'meson-sample.h']
girlib = shared_library(
- 'girlib',
+ 'gir_lib',
sources : libsources,
dependencies : gobj,
install : true
diff --git a/test cases/frameworks/7 gnome/installed_files.txt b/test cases/frameworks/7 gnome/installed_files.txt
index c922f8b..a18e445 100644
--- a/test cases/frameworks/7 gnome/installed_files.txt
+++ b/test cases/frameworks/7 gnome/installed_files.txt
@@ -3,6 +3,6 @@ usr/include/enums2.h
usr/include/enums3.h
usr/include/marshaller.h
usr/lib/girepository-1.0/Meson-1.0.typelib
-usr/lib/libgirlib.so
+usr/lib/libgir_lib.so
usr/share/gir-1.0/Meson-1.0.gir
usr/share/glib-2.0/schemas/com.github.meson.gschema.xml
diff --git a/test cases/vala/6 static library/installed_files.txt b/test cases/vala/6 static library/installed_files.txt
new file mode 100644
index 0000000..f464bc0
--- /dev/null
+++ b/test cases/vala/6 static library/installed_files.txt
@@ -0,0 +1 @@
+usr/lib/libextractedlib.a
diff --git a/test cases/vala/6 static library/meson.build b/test cases/vala/6 static library/meson.build
index ae8eeb9..c74bdf8 100644
--- a/test cases/vala/6 static library/meson.build
+++ b/test cases/vala/6 static library/meson.build
@@ -3,6 +3,12 @@ project('valastatic', 'vala', 'c')
valadeps = [dependency('glib-2.0'), dependency('gobject-2.0')]
l = static_library('valalib', 'mylib.vala', dependencies : valadeps)
+# NOTE: This static library is not usable from Vala because it does not carry
+# forward the .vapi and .h files generated by Valac to the next BuildTarget.
+# Will have to be fixed with https://github.com/mesonbuild/meson/issues/891
+m = static_library('extractedlib',
+ objects : l.extract_all_objects(),
+ install : true)
e = executable('valaprog', 'prog.vala',
link_with : l,