aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md2
-rw-r--r--docs/markdown/Icestorm-module.md6
-rw-r--r--docs/markdown/Project-templates.md2
-rw-r--r--mesonbuild/backend/ninjabackend.py10
-rw-r--r--mesonbuild/build.py8
-rw-r--r--mesonbuild/compilers/compilers.py29
-rw-r--r--mesonbuild/interpreter.py4
-rw-r--r--mesonbuild/mesonlib.py6
-rw-r--r--mesonbuild/mintro.py1
-rw-r--r--mesonbuild/modules/pkgconfig.py15
-rw-r--r--mesonbuild/scripts/yelphelper.py5
-rwxr-xr-xrun_unittests.py44
-rw-r--r--test cases/common/183 as-needed/config.h14
-rw-r--r--test cases/common/183 as-needed/libA.cpp7
-rw-r--r--test cases/common/183 as-needed/libA.h5
-rw-r--r--test cases/common/183 as-needed/libB.cpp19
-rw-r--r--test cases/common/183 as-needed/main.cpp7
-rw-r--r--test cases/common/183 as-needed/meson.build13
-rw-r--r--test cases/common/51 pkgconfig-gen/dependencies/meson.build2
-rw-r--r--test cases/unit/24 pkgconfig usage/dependee/meson.build7
-rw-r--r--test cases/unit/24 pkgconfig usage/dependee/pkguser.c6
-rw-r--r--test cases/unit/24 pkgconfig usage/dependency/meson.build24
-rw-r--r--test cases/unit/24 pkgconfig usage/dependency/pkgdep.c7
-rw-r--r--test cases/unit/24 pkgconfig usage/dependency/pkgdep.h3
-rw-r--r--test cases/unit/24 pkgconfig usage/dependency/privatelib.c3
25 files changed, 223 insertions, 26 deletions
diff --git a/README.md b/README.md
index 6185f8e..969e251 100644
--- a/README.md
+++ b/README.md
@@ -8,7 +8,7 @@ build system.
[![PyPI](https://img.shields.io/pypi/v/meson.svg)](https://pypi.python.org/pypi/meson)
[![Travis](https://travis-ci.org/mesonbuild/meson.svg?branch=master)](https://travis-ci.org/mesonbuild/meson)
-[![Appveyor](https://ci.appveyor.com/api/projects/status/l5c8v71ninew2i3p?svg=true)](https://ci.appveyor.com/project/jpakkane/meson)
+[![Appveyor](https://ci.appveyor.com/api/projects/status/7jfaotriu8d8ncov?svg=true)](https://ci.appveyor.com/project/mesonbuild/meson)
[![Codecov](https://codecov.io/gh/mesonbuild/meson/coverage.svg?branch=master)](https://codecov.io/gh/mesonbuild/meson/branch/master)
#### Dependencies
diff --git a/docs/markdown/Icestorm-module.md b/docs/markdown/Icestorm-module.md
index 6aa8481..bc2ad61 100644
--- a/docs/markdown/Icestorm-module.md
+++ b/docs/markdown/Icestorm-module.md
@@ -1,6 +1,6 @@
# Unstable IceStorm module
-This module provides is available since version 0.45.0.
+This module is available since version 0.45.0.
**Note**: this module is unstable. It is only provided as a technology
preview. Its API may change in arbitrary ways between releases or it
@@ -8,7 +8,7 @@ might be removed from Meson altogether.
## Usage
-This module provides an experimental to create FPGA bitstreams using
+This module provides an experimental method to create FPGA bitstreams using
the [IceStorm](http://www.clifford.at/icestorm/) suite of tools.
The module exposes only one method called `project` and it is used
@@ -24,4 +24,4 @@ constraint file. This produces output files called `projname.asc`,
`projname.blif` and `projname.bin`. In addition it creates two run
targets called `projname-time` for running timing analysis and
`projname-upload` that uploads the generated bitstream to an FPGA
-devide using the `iceprog` programming executable.
+device using the `iceprog` programming executable.
diff --git a/docs/markdown/Project-templates.md b/docs/markdown/Project-templates.md
index d8459c6..5f323bd 100644
--- a/docs/markdown/Project-templates.md
+++ b/docs/markdown/Project-templates.md
@@ -25,6 +25,6 @@ $ ninja -C builddir
```
The generator has many different projects and settings. They can all
-be listed by invoking the command `meson test --help`.
+be listed by invoking the command `meson init --help`.
This feature is available since Meson version 0.45.0.
diff --git a/mesonbuild/backend/ninjabackend.py b/mesonbuild/backend/ninjabackend.py
index 408e4d4..f0ea09b 100644
--- a/mesonbuild/backend/ninjabackend.py
+++ b/mesonbuild/backend/ninjabackend.py
@@ -27,7 +27,7 @@ from .. import compilers
from ..compilers import CompilerArgs
from ..linkers import ArLinker
from ..mesonlib import File, MesonException, OrderedSet
-from ..mesonlib import get_compiler_for_source
+from ..mesonlib import get_compiler_for_source, has_path_sep
from .backends import CleanTrees, InstallData
from ..build import InvalidArguments
@@ -1334,7 +1334,7 @@ int dummy;
# Set runtime-paths so we can run executables without needing to set
# LD_LIBRARY_PATH, etc in the environment. Doesn't work on Windows.
- if '/' in target.name or '\\' in target.name:
+ if has_path_sep(target.name):
# Target names really should not have slashes in them, but
# unfortunately we did not check for that and some downstream projects
# now have them. Once slashes are forbidden, remove this bit.
@@ -2323,7 +2323,7 @@ rule FORTRAN_DEP_HACK
# FIXME FIXME: The usage of this is a terrible and unreliable hack
if isinstance(fname, File):
return fname.subdir != ''
- return '/' in fname or '\\' in fname
+ return has_path_sep(fname)
# Fortran is a bit weird (again). When you link against a library, just compiling a source file
# requires the mod files that are output when single files are built. To do this right we would need to
@@ -2369,7 +2369,7 @@ rule FORTRAN_DEP_HACK
pch = target.get_pch(lang)
if not pch:
continue
- if '/' not in pch[0] or '/' not in pch[-1]:
+ if not has_path_sep(pch[0]) or not has_path_sep(pch[-1]):
msg = 'Precompiled header of {!r} must not be in the same ' \
'directory as source, please put it in a subdirectory.' \
''.format(target.get_basename())
@@ -2546,7 +2546,7 @@ rule FORTRAN_DEP_HACK
commands += linker.get_option_link_args(self.environment.coredata.compiler_options)
# Set runtime-paths so we can run executables without needing to set
# LD_LIBRARY_PATH, etc in the environment. Doesn't work on Windows.
- if '/' in target.name or '\\' in target.name:
+ if has_path_sep(target.name):
# Target names really should not have slashes in them, but
# unfortunately we did not check for that and some downstream projects
# now have them. Once slashes are forbidden, remove this bit.
diff --git a/mesonbuild/build.py b/mesonbuild/build.py
index 515fd83..c2f547b 100644
--- a/mesonbuild/build.py
+++ b/mesonbuild/build.py
@@ -23,7 +23,7 @@ from . import mlog
from .mesonlib import File, MesonException, listify, extract_as_list
from .mesonlib import typeslistify, stringlistify, classify_unity_sources
from .mesonlib import get_filenames_templates_dict, substitute_values
-from .mesonlib import for_windows, for_darwin, for_cygwin, for_android
+from .mesonlib import for_windows, for_darwin, for_cygwin, for_android, has_path_sep
from .compilers import is_object, clike_langs, sort_clike, lang_suffixes
known_basic_kwargs = {'install': True,
@@ -286,7 +286,7 @@ class EnvironmentVariables:
class Target:
def __init__(self, name, subdir, subproject, build_by_default):
- if '/' in name or '\\' in name:
+ if has_path_sep(name):
# Fix failing test 53 when this becomes an error.
mlog.warning('''Target "%s" has a path separator in its name.
This is not supported, it can cause unexpected failures and will become
@@ -1067,7 +1067,7 @@ class Generator:
raise InvalidArguments('"output" may only contain strings.')
if '@BASENAME@' not in rule and '@PLAINNAME@' not in rule:
raise InvalidArguments('Every element of "output" must contain @BASENAME@ or @PLAINNAME@.')
- if '/' in rule or '\\' in rule:
+ if has_path_sep(rule):
raise InvalidArguments('"outputs" must not contain a directory separator.')
if len(outputs) > 1:
for o in outputs:
@@ -1666,7 +1666,7 @@ class CustomTarget(Target):
raise InvalidArguments('Output must not be empty.')
if i.strip() == '':
raise InvalidArguments('Output must not consist only of whitespace.')
- if '/' in i:
+ if has_path_sep(i):
raise InvalidArguments('Output must not contain a path segment.')
if '@INPUT@' in i or '@INPUT0@' in i:
m = 'Output cannot contain @INPUT@ or @INPUT0@, did you ' \
diff --git a/mesonbuild/compilers/compilers.py b/mesonbuild/compilers/compilers.py
index 034fef4..f8dfc96 100644
--- a/mesonbuild/compilers/compilers.py
+++ b/mesonbuild/compilers/compilers.py
@@ -348,7 +348,7 @@ def get_base_link_args(options, linker, is_shared_module):
pass
try:
if 'b_asneeded' in linker.base_options and options['b_asneeded'].value:
- args.append('-Wl,--as-needed')
+ args.append(linker.get_asneeded_args())
except KeyError:
pass
try:
@@ -900,6 +900,13 @@ ICC_STANDARD = 0
ICC_OSX = 1
ICC_WIN = 2
+# GNU ld cannot be installed on macOS
+# https://github.com/Homebrew/homebrew-core/issues/17794#issuecomment-328174395
+# Hence, we don't need to differentiate between OS and ld
+# for the sake of adding as-needed support
+GNU_LD_AS_NEEDED = '-Wl,--as-needed'
+APPLE_LD_AS_NEEDED = '-Wl,-dead_strip_dylibs'
+
def get_gcc_soname_args(gcc_type, prefix, shlib_name, suffix, path, soversion, is_shared_module):
if soversion is None:
sostr = ''
@@ -1002,10 +1009,18 @@ class GnuCompiler:
'b_colorout', 'b_ndebug', 'b_staticpic']
if self.gcc_type != GCC_OSX:
self.base_options.append('b_lundef')
- self.base_options.append('b_asneeded')
+ self.base_options.append('b_asneeded')
# All GCC backends can do assembly
self.can_compile_suffixes.add('s')
+ # TODO: centralise this policy more globally, instead
+ # of fragmenting it into GnuCompiler and ClangCompiler
+ def get_asneeded_args(self):
+ if self.gcc_type == GCC_OSX:
+ return APPLE_LD_AS_NEEDED
+ else:
+ return GNU_LD_AS_NEEDED
+
def get_colorout_args(self, colortype):
if mesonlib.version_compare(self.version, '>=4.9.0'):
return gnu_color_args[colortype][:]
@@ -1084,10 +1099,18 @@ class ClangCompiler:
'b_ndebug', 'b_staticpic', 'b_colorout']
if self.clang_type != CLANG_OSX:
self.base_options.append('b_lundef')
- self.base_options.append('b_asneeded')
+ self.base_options.append('b_asneeded')
# All Clang backends can do assembly and LLVM IR
self.can_compile_suffixes.update(['ll', 's'])
+ # TODO: centralise this policy more globally, instead
+ # of fragmenting it into GnuCompiler and ClangCompiler
+ def get_asneeded_args(self):
+ if self.clang_type == CLANG_OSX:
+ return APPLE_LD_AS_NEEDED
+ else:
+ return GNU_LD_AS_NEEDED
+
def get_pic_args(self):
if self.clang_type in (CLANG_WIN, CLANG_OSX):
return [] # On Window and OS X, pic is always on.
diff --git a/mesonbuild/interpreter.py b/mesonbuild/interpreter.py
index 11e058c..029fe59 100644
--- a/mesonbuild/interpreter.py
+++ b/mesonbuild/interpreter.py
@@ -21,7 +21,7 @@ from . import optinterpreter
from . import compilers
from .wrap import wrap, WrapMode
from . import mesonlib
-from .mesonlib import FileMode, Popen_safe, listify, extract_as_list
+from .mesonlib import FileMode, Popen_safe, listify, extract_as_list, has_path_sep
from .dependencies import ExternalProgram
from .dependencies import InternalDependency, Dependency, DependencyException
from .interpreterbase import InterpreterBase
@@ -1863,7 +1863,7 @@ external dependencies (including libraries) must go to "dependencies".''')
raise InterpreterException('Subproject name must not contain a ".." path segment.')
if os.path.isabs(dirname):
raise InterpreterException('Subproject name must not be an absolute path.')
- if '\\' in dirname or '/' in dirname:
+ if has_path_sep(dirname):
mlog.warning('Subproject name has a path separator. This may cause unexpected behaviour.')
if dirname in self.subproject_stack:
fullstack = self.subproject_stack + [dirname]
diff --git a/mesonbuild/mesonlib.py b/mesonbuild/mesonlib.py
index 4e72600..247b4f9 100644
--- a/mesonbuild/mesonlib.py
+++ b/mesonbuild/mesonlib.py
@@ -519,6 +519,12 @@ def get_library_dirs():
unixdirs += glob('/lib/' + plat + '*')
return unixdirs
+def has_path_sep(name, sep='/\\'):
+ 'Checks if any of the specified @sep path separators are in @name'
+ for each in sep:
+ if each in name:
+ return True
+ return False
def do_replacement(regex, line, confdata):
missing_variables = set()
diff --git a/mesonbuild/mintro.py b/mesonbuild/mintro.py
index 1805e6c..23e666c 100644
--- a/mesonbuild/mintro.py
+++ b/mesonbuild/mintro.py
@@ -186,6 +186,7 @@ def list_tests(testdata):
to['workdir'] = t.workdir
to['timeout'] = t.timeout
to['suite'] = t.suite
+ to['is_parallel'] = t.is_parallel
result.append(to)
print(json.dumps(result))
diff --git a/mesonbuild/modules/pkgconfig.py b/mesonbuild/modules/pkgconfig.py
index 074fc5a..c89f657 100644
--- a/mesonbuild/modules/pkgconfig.py
+++ b/mesonbuild/modules/pkgconfig.py
@@ -96,7 +96,20 @@ class DependenciesHelper:
if obj.found():
processed_libs += obj.get_link_args()
processed_cflags += obj.get_compile_args()
- elif isinstance(obj, (build.SharedLibrary, build.StaticLibrary)):
+ elif isinstance(obj, build.SharedLibrary):
+ processed_libs.append(obj)
+ if public:
+ if not hasattr(obj, 'generated_pc'):
+ obj.generated_pc = self.name
+ elif isinstance(obj, build.StaticLibrary):
+ # Due to a "feature" in pkgconfig, it leaks out private dependencies.
+ # Thus we will not add them to the pc file unless the target
+ # we are processing is a static library.
+ #
+ # This way (hopefully) "pkgconfig --libs --static foobar" works
+ # and "pkgconfig --cflags/--libs foobar" does not have any trace
+ # of dependencies that the build file creator has not explicitly
+ # added to the dependency list.
processed_libs.append(obj)
if public:
if not hasattr(obj, 'generated_pc'):
diff --git a/mesonbuild/scripts/yelphelper.py b/mesonbuild/scripts/yelphelper.py
index ab99267..0f8b0b8 100644
--- a/mesonbuild/scripts/yelphelper.py
+++ b/mesonbuild/scripts/yelphelper.py
@@ -17,6 +17,7 @@ import subprocess
import shutil
import argparse
from .. import mlog
+from ..mesonlib import has_path_sep
from . import destdir_join
from .gettext import read_linguas
@@ -79,7 +80,7 @@ def install_help(srcdir, blddir, sources, media, langs, install_dir, destdir, pr
elif symlinks:
srcfile = os.path.join(c_install_dir, m)
mlog.log('Symlinking %s to %s.' % (outfile, srcfile))
- if '/' in m or '\\' in m:
+ if has_path_sep(m):
os.makedirs(os.path.dirname(outfile), exist_ok=True)
try:
try:
@@ -94,7 +95,7 @@ def install_help(srcdir, blddir, sources, media, langs, install_dir, destdir, pr
# Lang doesn't have media file so copy it over 'C' one
infile = os.path.join(srcdir, 'C', m)
mlog.log('Installing %s to %s' % (infile, outfile))
- if '/' in m or '\\' in m:
+ if has_path_sep(m):
os.makedirs(os.path.dirname(outfile), exist_ok=True)
shutil.copyfile(infile, outfile)
shutil.copystat(infile, outfile)
diff --git a/run_unittests.py b/run_unittests.py
index 6e9970e..3ea0412 100755
--- a/run_unittests.py
+++ b/run_unittests.py
@@ -513,7 +513,8 @@ class BasePlatformTests(unittest.TestCase):
windows_proof_rmtree(path)
except FileNotFoundError:
pass
- os.environ = self.orig_env
+ os.environ.clear()
+ os.environ.update(self.orig_env)
super().tearDown()
def _run(self, command, workdir=None):
@@ -588,10 +589,11 @@ class BasePlatformTests(unittest.TestCase):
def run_tests(self):
self._run(self.test_command, workdir=self.builddir)
- def install(self):
+ def install(self, *, use_destdir=True):
if self.backend is not Backend.ninja:
raise unittest.SkipTest('{!r} backend can\'t install files'.format(self.backend.name))
- os.environ['DESTDIR'] = self.installdir
+ if use_destdir:
+ os.environ['DESTDIR'] = self.installdir
self._run(self.install_command, workdir=self.builddir)
def uninstall(self):
@@ -2735,6 +2737,42 @@ endian = 'little'
self.build()
mesonbuild.modules.gnome.native_glib_version = None
+ @unittest.skipIf(shutil.which('pkg-config') is None, 'Pkg-config not found.')
+ def test_pkgconfig_usage(self):
+ testdir1 = os.path.join(self.unit_test_dir, '24 pkgconfig usage/dependency')
+ testdir2 = os.path.join(self.unit_test_dir, '24 pkgconfig usage/dependee')
+ if subprocess.call(['pkg-config', '--cflags', 'glib-2.0'],
+ stdout=subprocess.DEVNULL,
+ stderr=subprocess.DEVNULL) != 0:
+ raise unittest.SkipTest('Glib 2.0 dependency not available.')
+ with tempfile.TemporaryDirectory() as tempdirname:
+ self.init(testdir1, ['--prefix=' + tempdirname, '--libdir=lib'], default_args=False)
+ self.install(use_destdir=False)
+ shutil.rmtree(self.builddir)
+ os.mkdir(self.builddir)
+ pkg_dir = os.path.join(tempdirname, 'lib/pkgconfig')
+ self.assertTrue(os.path.exists(os.path.join(pkg_dir, 'libpkgdep.pc')))
+ lib_dir = os.path.join(tempdirname, 'lib')
+ os.environ['PKG_CONFIG_PATH'] = pkg_dir
+ # Private internal libraries must not leak out.
+ pkg_out = subprocess.check_output(['pkg-config', '--static', '--libs', 'libpkgdep'])
+ self.assertFalse(b'libpkgdep-int' in pkg_out, 'Internal library leaked out.')
+ # Dependencies must not leak to cflags when building only a shared library.
+ pkg_out = subprocess.check_output(['pkg-config', '--cflags', 'libpkgdep'])
+ self.assertFalse(b'glib' in pkg_out, 'Internal dependency leaked to headers.')
+ # Test that the result is usable.
+ self.init(testdir2)
+ self.build()
+ myenv = os.environ.copy()
+ myenv['LD_LIBRARY_PATH'] = lib_dir
+ if is_cygwin():
+ bin_dir = os.path.join(tempdirname, 'bin')
+ myenv['PATH'] = bin_dir + os.pathsep + myenv['PATH']
+ self.assertTrue(os.path.isdir(lib_dir))
+ test_exe = os.path.join(self.builddir, 'pkguser')
+ self.assertTrue(os.path.isfile(test_exe))
+ subprocess.check_call(test_exe, env=myenv)
+
class LinuxArmCrossCompileTests(BasePlatformTests):
'''
diff --git a/test cases/common/183 as-needed/config.h b/test cases/common/183 as-needed/config.h
new file mode 100644
index 0000000..b8fb60f
--- /dev/null
+++ b/test cases/common/183 as-needed/config.h
@@ -0,0 +1,14 @@
+#if defined _WIN32 || defined __CYGWIN__
+ #if defined BUILDING_DLL
+ #define DLL_PUBLIC __declspec(dllexport)
+ #else
+ #define DLL_PUBLIC __declspec(dllimport)
+ #endif
+#else
+ #if defined __GNUC__
+ #define DLL_PUBLIC __attribute__ ((visibility("default")))
+ #else
+ #pragma message ("Compiler does not support symbol visibility.")
+ #define DLL_PUBLIC
+ #endif
+#endif
diff --git a/test cases/common/183 as-needed/libA.cpp b/test cases/common/183 as-needed/libA.cpp
new file mode 100644
index 0000000..5f45bc0
--- /dev/null
+++ b/test cases/common/183 as-needed/libA.cpp
@@ -0,0 +1,7 @@
+#define BUILDING_DLL
+
+#include "libA.h"
+
+namespace meson_test_as_needed {
+ DLL_PUBLIC bool linked = false;
+}
diff --git a/test cases/common/183 as-needed/libA.h b/test cases/common/183 as-needed/libA.h
new file mode 100644
index 0000000..8e76d22
--- /dev/null
+++ b/test cases/common/183 as-needed/libA.h
@@ -0,0 +1,5 @@
+#include "config.h"
+
+namespace meson_test_as_needed {
+ DLL_PUBLIC extern bool linked;
+}
diff --git a/test cases/common/183 as-needed/libB.cpp b/test cases/common/183 as-needed/libB.cpp
new file mode 100644
index 0000000..a872394
--- /dev/null
+++ b/test cases/common/183 as-needed/libB.cpp
@@ -0,0 +1,19 @@
+#include "libA.h"
+
+#undef DLL_PUBLIC
+#define BUILDING_DLL
+#include "config.h"
+
+namespace meson_test_as_needed {
+ namespace {
+ bool set_linked() {
+ linked = true;
+ return true;
+ }
+ bool stub = set_linked();
+ }
+
+ DLL_PUBLIC int libB_unused_func() {
+ return 0;
+ }
+}
diff --git a/test cases/common/183 as-needed/main.cpp b/test cases/common/183 as-needed/main.cpp
new file mode 100644
index 0000000..cecb2ff
--- /dev/null
+++ b/test cases/common/183 as-needed/main.cpp
@@ -0,0 +1,7 @@
+#include <cstdlib>
+
+#include "libA.h"
+
+int main() {
+ return (meson_test_as_needed::linked == false ? EXIT_SUCCESS : EXIT_FAILURE);
+}
diff --git a/test cases/common/183 as-needed/meson.build b/test cases/common/183 as-needed/meson.build
new file mode 100644
index 0000000..3b54aaa
--- /dev/null
+++ b/test cases/common/183 as-needed/meson.build
@@ -0,0 +1,13 @@
+project('as-needed test', 'cpp')
+
+# Idea behind this test is to have -Wl,--as-needed prune
+# away unneeded linkages, which would otherwise cause global
+# static initialiser side-effects to set a boolean to true.
+
+# Credits for portable ISO C++ idea go to sarum9in
+
+libA = library('A', 'libA.cpp')
+libB = library('B', 'libB.cpp', link_with : libA)
+
+main_exe = executable('C', 'main.cpp', link_with : [libA, libB])
+test('main test', main_exe)
diff --git a/test cases/common/51 pkgconfig-gen/dependencies/meson.build b/test cases/common/51 pkgconfig-gen/dependencies/meson.build
index 018b72f..2e00943 100644
--- a/test cases/common/51 pkgconfig-gen/dependencies/meson.build
+++ b/test cases/common/51 pkgconfig-gen/dependencies/meson.build
@@ -5,7 +5,7 @@ pkgg = import('pkgconfig')
# libmain internally use libinternal and expose libexpose in its API
exposed_lib = shared_library('libexposed', 'exposed.c')
internal_lib = shared_library('libinternal', 'internal.c')
-main_lib = shared_library('libmain', link_with : [exposed_lib, internal_lib])
+main_lib = static_library('libmain', link_with : [exposed_lib, internal_lib])
pkgg.generate(libraries : exposed_lib,
version : '1.0',
diff --git a/test cases/unit/24 pkgconfig usage/dependee/meson.build b/test cases/unit/24 pkgconfig usage/dependee/meson.build
new file mode 100644
index 0000000..beb446c
--- /dev/null
+++ b/test cases/unit/24 pkgconfig usage/dependee/meson.build
@@ -0,0 +1,7 @@
+project('pkgconfig user', 'c')
+
+pkgdep = dependency('libpkgdep')
+
+executable('pkguser', 'pkguser.c',
+ dependencies : pkgdep)
+
diff --git a/test cases/unit/24 pkgconfig usage/dependee/pkguser.c b/test cases/unit/24 pkgconfig usage/dependee/pkguser.c
new file mode 100644
index 0000000..2bff316
--- /dev/null
+++ b/test cases/unit/24 pkgconfig usage/dependee/pkguser.c
@@ -0,0 +1,6 @@
+#include<pkgdep.h>
+
+int main(int argc, char **argv) {
+ int res = pkgdep();
+ return res != 99;
+}
diff --git a/test cases/unit/24 pkgconfig usage/dependency/meson.build b/test cases/unit/24 pkgconfig usage/dependency/meson.build
new file mode 100644
index 0000000..89fae8e
--- /dev/null
+++ b/test cases/unit/24 pkgconfig usage/dependency/meson.build
@@ -0,0 +1,24 @@
+project('pkgconfig dep', 'c',
+ version : '1.0.0')
+
+# This is not used in the code, only to check that it does not
+# leak out to --libs.
+glib_dep = dependency('glib-2.0')
+
+pkgconfig = import('pkgconfig')
+
+intlib = static_library('libpkgdep-int', 'privatelib.c')
+intdep = declare_dependency(link_with : intlib)
+
+lib = shared_library('pkgdep', 'pkgdep.c',
+ dependencies : [glib_dep, intdep],
+ install : true)
+
+install_headers('pkgdep.h')
+
+pkgconfig.generate(
+ filebase : 'libpkgdep',
+ name : 'Libpkgdep',
+ description : 'Sample pkgconfig dependency library',
+ version : meson.project_version(),
+ libraries : lib)
diff --git a/test cases/unit/24 pkgconfig usage/dependency/pkgdep.c b/test cases/unit/24 pkgconfig usage/dependency/pkgdep.c
new file mode 100644
index 0000000..bd5c3f4
--- /dev/null
+++ b/test cases/unit/24 pkgconfig usage/dependency/pkgdep.c
@@ -0,0 +1,7 @@
+#include<pkgdep.h>
+
+int internal_thingy();
+
+int pkgdep() {
+ return internal_thingy();
+}
diff --git a/test cases/unit/24 pkgconfig usage/dependency/pkgdep.h b/test cases/unit/24 pkgconfig usage/dependency/pkgdep.h
new file mode 100644
index 0000000..16d622e
--- /dev/null
+++ b/test cases/unit/24 pkgconfig usage/dependency/pkgdep.h
@@ -0,0 +1,3 @@
+#pragma once
+
+int pkgdep();
diff --git a/test cases/unit/24 pkgconfig usage/dependency/privatelib.c b/test cases/unit/24 pkgconfig usage/dependency/privatelib.c
new file mode 100644
index 0000000..71d2179
--- /dev/null
+++ b/test cases/unit/24 pkgconfig usage/dependency/privatelib.c
@@ -0,0 +1,3 @@
+int internal_thingy() {
+ return 99;
+}