| From afcd4a146fb82843f6ff695f89504ce4ca65ddfd Mon Sep 17 00:00:00 2001 |
| From: David 'Digit' Turner <digit+github@google.com> |
| Date: Sun, 12 May 2024 23:45:28 +0200 |
| Subject: [PATCH] configure.py: Support --gtest-source-dir to build tests. |
| |
| Allow the Ninja build plan generated by configure.py to |
| build `ninja_test` by compiling GoogleTest from source if |
| the path to the library if passed through the new option |
| `--gtest-source-dir` or the GTEST_SOURCE_DIR environment |
| variable. |
| |
| For simplicity, probing for an installed version of the |
| library, and linking to it, is not supported (use the |
| CMake build for this). |
| |
| This also removes the obsolete `--gtest-dir` option. |
| |
| + Update README.md |
| |
| Fixes #2447 |
| --- |
| README.md | 13 ++++++++ |
| configure.py | 83 +++++++++++++++++++++++++++++++++++++++++++++++++++- |
| 2 files changed, 95 insertions(+), 1 deletion(-) |
| |
| --- a/README.md |
| +++ b/README.md |
| @@ -34,6 +34,19 @@ via CMake. For more details see |
| This will generate the `ninja` binary and a `build.ninja` file you can now use |
| to build Ninja with itself. |
| |
| +If you have a GoogleTest source directory, you can build the tests |
| +by passing its path with `--gtest-source-dir=PATH` option, or the |
| +`GTEST_SOURCE_DIR` environment variable, e.g.: |
| + |
| +``` |
| +./configure.py --bootstrap --gtest-source-dir=/path/to/googletest |
| +./ninja all # build ninja_test and other auxiliary binaries |
| +./ninja_test` # run the unit-test suite. |
| +``` |
| + |
| +Use the CMake build below if you want to use a preinstalled binary |
| +version of the library. |
| + |
| ### CMake |
| |
| ``` |
| --- a/configure.py |
| +++ b/configure.py |
| @@ -213,7 +213,10 @@ parser.add_option('--debug', action='sto |
| parser.add_option('--profile', metavar='TYPE', |
| choices=profilers, |
| help='enable profiling (' + '/'.join(profilers) + ')',) |
| -parser.add_option('--with-gtest', metavar='PATH', help='ignored') |
| +parser.add_option('--gtest-source-dir', metavar='PATH', |
| + help='Path to GoogleTest source directory. If not provided ' + |
| + 'GTEST_SOURCE_DIR will be probed in the environment. ' + |
| + 'Tests will not be built without a value.') |
| parser.add_option('--with-python', metavar='EXE', |
| help='use EXE as the Python interpreter', |
| default=os.path.basename(sys.executable)) |
| @@ -425,6 +428,7 @@ n.variable('cflags', ' '.join(shell_esca |
| if 'LDFLAGS' in configure_env: |
| ldflags.append(configure_env['LDFLAGS']) |
| n.variable('ldflags', ' '.join(shell_escape(flag) for flag in ldflags)) |
| + |
| n.newline() |
| |
| if platform.is_msvc(): |
| @@ -582,6 +586,83 @@ if options.bootstrap: |
| # build.ninja file. |
| n = ninja_writer |
| |
| +# Build the ninja_test executable only if the GTest source directory |
| +# is provided explicitly. Either from the environment with GTEST_SOURCE_DIR |
| +# or with the --gtest-source-dir command-line option. |
| +# |
| +# Do not try to look for an installed binary version, and link against it |
| +# because doing so properly is platform-specific (use the CMake build for |
| +# this). |
| +if options.gtest_source_dir: |
| + gtest_src_dir = options.gtest_source_dir |
| +else: |
| + gtest_src_dir = os.environ.get('GTEST_SOURCE_DIR') |
| + |
| +if gtest_src_dir: |
| + # Verify GoogleTest source directory, and add its include directory |
| + # to the global include search path (even for non-test sources) to |
| + # keep the build plan generation simple. |
| + gtest_all_cc = os.path.join(gtest_src_dir, 'googletest', 'src', 'gtest-all.cc') |
| + if not os.path.exists(gtest_all_cc): |
| + print('ERROR: Missing GoogleTest source file: %s' % gtest_all_cc) |
| + sys.exit(1) |
| + |
| + n.comment('Tests all build into ninja_test executable.') |
| + |
| + # Test-specific version of cflags, must include the GoogleTest |
| + # include directory. Also GoogleTest can only build with a C++14 compiler. |
| + test_cflags = [f.replace('std=c++11', 'std=c++14') for f in cflags] |
| + test_cflags.append('-I' + os.path.join(gtest_src_dir, 'googletest', 'include')) |
| + |
| + test_variables = [('cflags', test_cflags)] |
| + if platform.is_msvc(): |
| + test_variables += [('pdb', 'ninja_test.pdb')] |
| + |
| + test_names = [ |
| + 'build_log_test', |
| + 'build_test', |
| + 'clean_test', |
| + 'clparser_test', |
| + 'depfile_parser_test', |
| + 'deps_log_test', |
| + 'disk_interface_test', |
| + 'dyndep_parser_test', |
| + 'edit_distance_test', |
| + 'graph_test', |
| + 'json_test', |
| + 'lexer_test', |
| + 'manifest_parser_test', |
| + 'ninja_test', |
| + 'state_test', |
| + 'string_piece_util_test', |
| + 'subprocess_test', |
| + 'test', |
| + 'util_test', |
| + ] |
| + if platform.is_windows(): |
| + test_names += [ |
| + 'includes_normalize_test', |
| + 'msvc_helper_test', |
| + ] |
| + |
| + objs = [] |
| + for name in test_names: |
| + objs += cxx(name, variables=test_variables) |
| + |
| + # Build GTest as a monolithic source file. |
| + # This requires one extra include search path, so replace the |
| + # value of 'cflags' in our list. |
| + gtest_all_variables = test_variables[1:] + [ |
| + ('cflags', test_cflags + ['-I' + os.path.join(gtest_src_dir, 'googletest') ]), |
| + ] |
| + # Do not use cxx() directly to ensure the object file is under $builddir. |
| + objs += n.build(built('gtest_all' + objext), 'cxx', gtest_all_cc, variables=gtest_all_variables) |
| + |
| + ninja_test = n.build(binary('ninja_test'), 'link', objs, implicit=ninja_lib, |
| + variables=[('libs', libs)]) |
| + n.newline() |
| + all_targets += ninja_test |
| + |
| n.comment('Ancillary executables.') |
| |
| if platform.is_aix() and '-maix64' not in ldflags: |