quality / test: Fortran type hinting

enhance fortran args tests
pull/6908/head
Michael Hirsch, Ph.D 5 years ago committed by Jussi Pakkanen
parent df5113252b
commit 5b4ebb5641
  1. 31
      mesonbuild/compilers/fortran.py
  2. 10
      mesonbuild/compilers/mixins/clike.py
  3. 18
      mesonbuild/interpreter.py
  4. 2
      test cases/fortran/18 first_arg/main.f90
  5. 20
      test cases/fortran/18 first_arg/meson.build

@ -142,14 +142,15 @@ class FortranCompiler(CLikeCompiler, Compiler):
return filename
def find_library(self, libname, env, extra_dirs, libtype: LibType = LibType.PREFER_SHARED):
code = '''stop; end program'''
code = 'stop; end program'
return self.find_library_impl(libname, env, extra_dirs, code, libtype)
def has_multi_arguments(self, args, env):
def has_multi_arguments(self, args: T.Sequence[str], env):
for arg in args[:]:
# some compilers, e.g. GCC, don't warn for unsupported warning-disable
# flags, so when we are testing a flag like "-Wno-forgotten-towel", also
# check the equivalent enable flag too "-Wforgotten-towel"
# GCC does error for "-fno-foobar"
if arg.startswith('-Wno-'):
args.append('-W' + arg[5:])
if arg.startswith('-Wl,'):
@ -197,16 +198,16 @@ class GnuFortranCompiler(GnuCompiler, FortranCompiler):
args.append('-std=' + std.value)
return args
def get_dependency_gen_args(self, outtarget, outfile):
def get_dependency_gen_args(self, outtarget, outfile) -> T.List[str]:
# Disabled until this is fixed:
# https://gcc.gnu.org/bugzilla/show_bug.cgi?id=62162
# return ['-cpp', '-MD', '-MQ', outtarget]
return []
def get_module_outdir_args(self, path):
def get_module_outdir_args(self, path: str) -> T.List[str]:
return ['-J' + path]
def language_stdlib_only_link_flags(self):
def language_stdlib_only_link_flags(self) -> T.List[str]:
return ['-lgfortran', '-lm']
class ElbrusFortranCompiler(GnuFortranCompiler, ElbrusCompiler):
@ -233,7 +234,7 @@ class G95FortranCompiler(FortranCompiler):
'2': default_warn_args + ['-Wextra'],
'3': default_warn_args + ['-Wextra', '-pedantic']}
def get_module_outdir_args(self, path):
def get_module_outdir_args(self, path: str) -> T.List[str]:
return ['-fmod=' + path]
def get_no_warn_args(self):
@ -251,7 +252,7 @@ class SunFortranCompiler(FortranCompiler):
FortranCompiler.__init__(self, exelist, version, for_machine, is_cross, info, exe_wrapper, **kwargs)
self.id = 'sun'
def get_dependency_gen_args(self, outtarget, outfile):
def get_dependency_gen_args(self, outtarget, outfile) -> T.List[str]:
return ['-fpp']
def get_always_args(self):
@ -263,10 +264,10 @@ class SunFortranCompiler(FortranCompiler):
def get_module_incdir_args(self):
return ('-M', )
def get_module_outdir_args(self, path):
def get_module_outdir_args(self, path: str) -> T.List[str]:
return ['-moddir=' + path]
def openmp_flags(self):
def openmp_flags(self) -> T.List[str]:
return ['-xopenmp']
@ -304,7 +305,7 @@ class IntelFortranCompiler(IntelGnuLikeCompiler, FortranCompiler):
args.append('-stand=' + stds[std.value])
return args
def get_preprocess_only_args(self):
def get_preprocess_only_args(self) -> T.List[str]:
return ['-cpp', '-EP']
def get_always_args(self):
@ -313,7 +314,7 @@ class IntelFortranCompiler(IntelGnuLikeCompiler, FortranCompiler):
val.remove('-pipe')
return val
def language_stdlib_only_link_flags(self):
def language_stdlib_only_link_flags(self) -> T.List[str]:
return ['-lifcore', '-limf']
def get_dependency_gen_args(self, outtarget: str, outfile: str) -> T.List[str]:
@ -371,7 +372,7 @@ class PathScaleFortranCompiler(FortranCompiler):
'2': default_warn_args,
'3': default_warn_args}
def openmp_flags(self):
def openmp_flags(self) -> T.List[str]:
return ['-mp']
@ -423,7 +424,7 @@ class Open64FortranCompiler(FortranCompiler):
'2': default_warn_args,
'3': default_warn_args}
def openmp_flags(self):
def openmp_flags(self) -> T.List[str]:
return ['-mp']
@ -438,8 +439,8 @@ class NAGFortranCompiler(FortranCompiler):
def get_warn_args(self, level):
return []
def get_module_outdir_args(self, path):
def get_module_outdir_args(self, path) -> T.List[str]:
return ['-mdir', path]
def openmp_flags(self):
def openmp_flags(self) -> T.List[str]:
return ['-openmp']

@ -319,7 +319,7 @@ class CLikeCompiler:
cargs += self.get_compiler_args_for_mode(mode)
return cargs, largs
def _get_compiler_check_args(self, env, extra_args, dependencies, mode='compile'):
def _get_compiler_check_args(self, env, extra_args: list, dependencies, mode: str = 'compile') -> T.List[str]:
if extra_args is None:
extra_args = []
else:
@ -354,11 +354,13 @@ class CLikeCompiler:
args = cargs + extra_args + largs
return args
def compiles(self, code, env, *, extra_args=None, dependencies=None, mode='compile', disable_cache=False):
def compiles(self, code: str, env, *,
extra_args: T.Sequence[T.Union[T.Sequence[str], str]] = None,
dependencies=None, mode: str = 'compile', disable_cache=False) -> T.Tuple[bool, bool]:
with self._build_wrapper(code, env, extra_args, dependencies, mode, disable_cache=disable_cache) as p:
return p.returncode == 0, p.cached
def _build_wrapper(self, code, env, extra_args, dependencies=None, mode='compile', want_output=False, disable_cache=False, temp_dir=None):
def _build_wrapper(self, code: str, env, extra_args, dependencies=None, mode: str = 'compile', want_output: bool = False, disable_cache: bool = False, temp_dir=None) -> T.Tuple[bool, bool]:
args = self._get_compiler_check_args(env, extra_args, dependencies, mode)
if disable_cache or want_output:
return self.compile(code, extra_args=args, mode=mode, want_output=want_output, temp_dir=env.scratch_dir)
@ -1074,7 +1076,7 @@ class CLikeCompiler:
def linker_to_compiler_args(self, args):
return args
def has_arguments(self, args, env, code, mode):
def has_arguments(self, args: T.Sequence[str], env, code: str, mode: str) -> T.Tuple[bool, bool]:
return self.compiles(code, env, extra_args=args, mode=mode)
def has_multi_arguments(self, args, env):

@ -1,4 +1,4 @@
# Copyright 2012-2018 The Meson development team
# Copyright 2012-2019 The Meson development team
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
@ -1621,14 +1621,14 @@ class CompilerHolder(InterpreterObject):
return ExternalLibraryHolder(lib, self.subproject)
@permittedKwargs({})
def has_argument_method(self, args, kwargs):
def has_argument_method(self, args: T.Sequence[str], kwargs) -> bool:
args = mesonlib.stringlistify(args)
if len(args) != 1:
raise InterpreterException('has_argument takes exactly one argument.')
return self.has_multi_arguments_method(args, kwargs)
@permittedKwargs({})
def has_multi_arguments_method(self, args, kwargs):
def has_multi_arguments_method(self, args: T.Sequence[str], kwargs: dict):
args = mesonlib.stringlistify(args)
result, cached = self.compiler.has_multi_arguments(args, self.environment)
if result:
@ -1653,11 +1653,11 @@ class CompilerHolder(InterpreterObject):
return supported_args
@permittedKwargs({})
def first_supported_argument_method(self, args, kwargs):
for i in mesonlib.stringlistify(args):
if self.has_argument_method(i, kwargs):
mlog.log('First supported argument:', mlog.bold(i))
return [i]
def first_supported_argument_method(self, args: T.Sequence[str], kwargs: dict) -> T.List[str]:
for arg in mesonlib.stringlistify(args):
if self.has_argument_method(arg, kwargs):
mlog.log('First supported argument:', mlog.bold(arg))
return [arg]
mlog.log('First supported argument:', mlog.red('None'))
return []
@ -3601,7 +3601,7 @@ external dependencies (including libraries) must go to "dependencies".''')
if 'input' not in kwargs or 'output' not in kwargs:
raise InterpreterException('Keyword arguments input and output must exist')
if 'fallback' not in kwargs:
FeatureNew('T.Optional fallback in vcs_tag', '0.41.0').use(self.subproject)
FeatureNew('Optional fallback in vcs_tag', '0.41.0').use(self.subproject)
fallback = kwargs.pop('fallback', self.project_version)
if not isinstance(fallback, str):
raise InterpreterException('Keyword argument fallback must be a string.')

@ -24,3 +24,23 @@ l2 = fc.first_supported_argument(isnt_arg, isnt_arg, isnt_arg)
assert(l1.length() == 1, 'First supported returned wrong result.')
assert(l1.get(0) == is_arg, 'First supported returned wrong argument.')
assert(l2.length() == 0, 'First supported did not return empty array.')
# --- test with an actual program, here for implicit none
in0 = fc.first_supported_argument('-fimplicit-none', '-Mdclchk', '/warn:declarations', '-warn').get(0, '')
impnone = {
'intel-cl': '/warn:declarations',
'intel': '-warn',
'gcc': '-fimplicit-none',
'pgi': '-Mdclchk',
}
arg = impnone.get(fc.get_id(), '')
if arg != ''
assert(in0 == arg, 'implicit none argument ' + arg + ' not matching ' + in0)
endif
in1 = fc.get_supported_arguments('-fimplicit-none', '/warn:declarations', '/warn:errors', '-Mdclchk')
if in1.length() > 0
assert(not fc.compiles(files('main.f90'), args: in1, name:'will fail implicit none'), 'implicit none should have failed')
endif

Loading…
Cancel
Save