aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJussi Pakkanen <jpakkane@gmail.com>2018-08-11 19:59:34 +0300
committerGitHub <noreply@github.com>2018-08-11 19:59:34 +0300
commitf91b463bf4625bfc167b78b52f091f45cddfdff4 (patch)
tree13747f96c8f68d8b6bb1b4a442de755a6cdb8ae4
parentf80c11e7ee4f521b1b4e3af56293fdcac15676fe (diff)
parentfb2cdd0fe2797b30e1fd4c118407302402739a3b (diff)
downloadmeson-f91b463bf4625bfc167b78b52f091f45cddfdff4.zip
meson-f91b463bf4625bfc167b78b52f091f45cddfdff4.tar.gz
meson-f91b463bf4625bfc167b78b52f091f45cddfdff4.tar.bz2
Merge pull request #3831 from mesonbuild/symvisibility
Add gnu_symbol_visibility keyword argument
-rw-r--r--docs/markdown/Reference-manual.md16
-rw-r--r--docs/markdown/snippets/visibility.md13
-rw-r--r--mesonbuild/backend/ninjabackend.py2
-rw-r--r--mesonbuild/build.py9
-rw-r--r--mesonbuild/compilers/compilers.py15
-rw-r--r--mesonbuild/interpreter.py1
-rw-r--r--mesonbuild/minit.py16
-rw-r--r--test cases/failing build/2 hidden symbol/bob.c5
-rw-r--r--test cases/failing build/2 hidden symbol/bob.h3
-rw-r--r--test cases/failing build/2 hidden symbol/bobuser.c5
-rw-r--r--test cases/failing build/2 hidden symbol/meson.build14
11 files changed, 81 insertions, 18 deletions
diff --git a/docs/markdown/Reference-manual.md b/docs/markdown/Reference-manual.md
index 12018fc..a7b8a2b 100644
--- a/docs/markdown/Reference-manual.md
+++ b/docs/markdown/Reference-manual.md
@@ -511,6 +511,13 @@ be passed to [shared and static libraries](#library).
- `override_options` takes an array of strings in the same format as
`project`'s `default_options` overriding the values of these options
for this target only, since 0.40.0
+- `gnu_symbol_visibility` specifies how symbols should be exported, see
+ e.g [the GCC Wiki](https://gcc.gnu.org/wiki/Visibility) for more
+ information. This value can either be an empty string or one of
+ `default`, `internal`, `hidden`, `protected` or `inlineshidden`, which
+ is the same as `hidden` but also includes things like C++ implicit
+ constructors as specified in the GCC manual. Ignored on compilers that
+ do not support GNU visibility arguments. Available since 0.48.0.
- `d_import_dirs` list of directories to look in for string imports used
in the D programming language
- `d_unittest`, when set to true, the D modules are compiled in debug mode
@@ -976,15 +983,16 @@ dropped. That means that `join_paths('foo', '/bar')` returns `/bar`.
buildtarget library(library_name, list_of_sources, ...)
```
-Builds a library that is either static, shared or both depending on the value of
-`default_library` user option. You should use this instead of
-[`shared_library`](#shared_library),
+Builds a library that is either static, shared or both depending on
+the value of `default_library` user option. You should use this
+instead of [`shared_library`](#shared_library),
[`static_library`](#static_library) or
[`both_libraries`](#both_libraries) most of the time. This allows you
to toggle your entire project (including subprojects) from shared to
static with only one option.
-The keyword arguments for this are the same as for [`executable`](#executable) with the following additions:
+The keyword arguments for this are the same as for
+[`executable`](#executable) with the following additions:
- `name_prefix` the string that will be used as the prefix for the
target output filename by overriding the default (only used for
diff --git a/docs/markdown/snippets/visibility.md b/docs/markdown/snippets/visibility.md
new file mode 100644
index 0000000..4b67105
--- /dev/null
+++ b/docs/markdown/snippets/visibility.md
@@ -0,0 +1,13 @@
+## Keyword argument for GNU symbol visibility
+
+Build targets got a new keyword, `symbol_visibility` that controls how
+symbols are exported from shared libraries. This is most commonly used
+to hide implementation symbols like this:
+
+```meson
+shared_library('mylib', ...
+ gnu_symbol_visibility: 'hidden')
+```
+
+In this case only symbols explicitly marked as visible in the source
+files get exported.
diff --git a/mesonbuild/backend/ninjabackend.py b/mesonbuild/backend/ninjabackend.py
index 913830f..9dcf0fa 100644
--- a/mesonbuild/backend/ninjabackend.py
+++ b/mesonbuild/backend/ninjabackend.py
@@ -1951,6 +1951,8 @@ rule FORTRAN_DEP_HACK%s
# Create an empty commands list, and start adding arguments from
# various sources in the order in which they must override each other
commands = CompilerArgs(compiler)
+ # Start with symbol visibility.
+ commands += compiler.gnu_symbol_visibility_args(target.gnu_symbol_visibility)
# Add compiler args for compiling this target derived from 'base' build
# options passed on the command-line, in default_options, etc.
# These have the lowest priority.
diff --git a/mesonbuild/build.py b/mesonbuild/build.py
index a3cd993..c1cb8a8 100644
--- a/mesonbuild/build.py
+++ b/mesonbuild/build.py
@@ -71,6 +71,7 @@ buildtarget_kwargs = set([
'objects',
'override_options',
'sources',
+ 'gnu_symbol_visibility',
])
known_build_target_kwargs = (
@@ -817,6 +818,14 @@ This will become a hard error in a future Meson release.''')
self.implicit_include_directories = kwargs.get('implicit_include_directories', True)
if not isinstance(self.implicit_include_directories, bool):
raise InvalidArguments('Implicit_include_directories must be a boolean.')
+ self.gnu_symbol_visibility = kwargs.get('gnu_symbol_visibility', '')
+ if not isinstance(self.gnu_symbol_visibility, str):
+ raise InvalidArguments('GNU symbol visibility must be a string.')
+ if self.gnu_symbol_visibility != '':
+ permitted = ['default', 'internal', 'hidden', 'protected', 'inlineshidden']
+ if self.gnu_symbol_visibility not in permitted:
+ raise InvalidArguments('GNU symbol visibility arg %s not one of: %s',
+ self.symbol_visibility, ', '.join(permitted))
def get_filename(self):
return self.filename
diff --git a/mesonbuild/compilers/compilers.py b/mesonbuild/compilers/compilers.py
index cb3ed23..ea0fc2c 100644
--- a/mesonbuild/compilers/compilers.py
+++ b/mesonbuild/compilers/compilers.py
@@ -311,6 +311,14 @@ vs64_instruction_set_args = {'mmx': ['/arch:AVX'],
'neon': None,
}
+gnu_symbol_visibility_args = {'': [],
+ 'default': ['-fvisibility=default'],
+ 'internal': ['-fvisibility=internal'],
+ 'hidden': ['-fvisibility=hidden'],
+ 'protected': ['-fvisibility=protected'],
+ 'inlineshidden': ['-fvisibility=hidden', '-fvisibility-inlines-hidden'],
+ }
+
def sanitizer_compile_args(value):
if value == 'none':
return []
@@ -1065,6 +1073,9 @@ class Compiler:
# building fails with undefined symbols.
return []
+ def gnu_symbol_visibility_args(self, vistype):
+ return []
+
GCC_STANDARD = 0
GCC_OSX = 1
GCC_MINGW = 2
@@ -1280,6 +1291,8 @@ class GnuCompiler:
def openmp_flags(self):
return ['-fopenmp']
+ def gnu_symbol_visibility_args(self, vistype):
+ return gnu_symbol_visibility_args[vistype]
class ElbrusCompiler(GnuCompiler):
# Elbrus compiler is nearly like GCC, but does not support
@@ -1422,6 +1435,8 @@ class ClangCompiler:
# Shouldn't work, but it'll be checked explicitly in the OpenMP dependency.
return []
+ def gnu_symbol_visibility_args(self, vistype):
+ return gnu_symbol_visibility_args[vistype]
class ArmclangCompiler:
def __init__(self):
diff --git a/mesonbuild/interpreter.py b/mesonbuild/interpreter.py
index 50d6148..1cf20f8 100644
--- a/mesonbuild/interpreter.py
+++ b/mesonbuild/interpreter.py
@@ -3854,6 +3854,7 @@ Try setting b_lundef to false instead.''')
@FeatureNewKwargs('build target', '0.42.0', ['rust_crate_type', 'build_rpath', 'implicit_include_directories'])
@FeatureNewKwargs('build target', '0.41.0', ['rust_args'])
@FeatureNewKwargs('build target', '0.40.0', ['build_by_default'])
+ @FeatureNewKwargs('build target', '0.48.0', ['gnu_symbol_visibility'])
def build_target_decorator_caller(self, node, args, kwargs):
return True
diff --git a/mesonbuild/minit.py b/mesonbuild/minit.py
index 1a83ed2..a66361f 100644
--- a/mesonbuild/minit.py
+++ b/mesonbuild/minit.py
@@ -72,16 +72,10 @@ lib_c_meson_template = '''project('{project_name}', 'c',
# not the executables that use the library.
lib_args = ['-DBUILDING_{utoken}']
-# Hiding symbols that are not explicitly marked as exported
-# requires a compiler flag on all compilers except VS.
-cc = meson.get_compiler('c')
-if cc.get_id() != 'msvc'
- lib_args += ['-fvisibility=hidden']
-endif
-
shlib = shared_library('{lib_name}', '{source_file}',
install : true,
c_args : lib_args,
+ gnu_symbol_visibility : 'hidden',
)
test_exe = executable('{test_exe_name}', '{test_source_file}',
@@ -226,16 +220,10 @@ lib_cpp_meson_template = '''project('{project_name}', 'cpp',
# not the executables that use the library.
lib_args = ['-DBUILDING_{utoken}']
-# Hiding symbols that are not explicitly marked as exported
-# requires a compiler flag on all compilers except VS.
-cpp = meson.get_compiler('cpp')
-if cpp.get_id() != 'msvc'
- lib_args += ['-fvisibility=hidden']
-endif
-
shlib = shared_library('{lib_name}', '{source_file}',
install : true,
cpp_args : lib_args,
+ gnu_symbol_visibility : 'hidden',
)
test_exe = executable('{test_exe_name}', '{test_source_file}',
diff --git a/test cases/failing build/2 hidden symbol/bob.c b/test cases/failing build/2 hidden symbol/bob.c
new file mode 100644
index 0000000..9a3325a
--- /dev/null
+++ b/test cases/failing build/2 hidden symbol/bob.c
@@ -0,0 +1,5 @@
+#include"bob.h"
+
+int hidden_function() {
+ return 7;
+}
diff --git a/test cases/failing build/2 hidden symbol/bob.h b/test cases/failing build/2 hidden symbol/bob.h
new file mode 100644
index 0000000..947f6ee
--- /dev/null
+++ b/test cases/failing build/2 hidden symbol/bob.h
@@ -0,0 +1,3 @@
+#pragma once
+
+int hidden_function();
diff --git a/test cases/failing build/2 hidden symbol/bobuser.c b/test cases/failing build/2 hidden symbol/bobuser.c
new file mode 100644
index 0000000..89272ed
--- /dev/null
+++ b/test cases/failing build/2 hidden symbol/bobuser.c
@@ -0,0 +1,5 @@
+#include"bob.h"
+
+int main(int argc, char **argv) {
+ return hidden_function();
+}
diff --git a/test cases/failing build/2 hidden symbol/meson.build b/test cases/failing build/2 hidden symbol/meson.build
new file mode 100644
index 0000000..0527347
--- /dev/null
+++ b/test cases/failing build/2 hidden symbol/meson.build
@@ -0,0 +1,14 @@
+project('hidden symbol', 'c')
+
+if host_machine.system() == 'windows' or host_machine.system() == 'cygwin'
+ cc = meson.get_compiler('c')
+ if cc.get_id() == 'gcc'
+ error('MESON_SKIP_TEST -fvisibility=hidden does not work on MinGW or Cygwin.')
+ endif
+endif
+
+l = shared_library('bob', 'bob.c',
+ gnu_symbol_visibility: 'hidden')
+
+executable('bobuser', 'bobuser.c',
+ link_with: l)