From 060804deb8c05b5ea5735b875eaea2c7493e2262 Mon Sep 17 00:00:00 2001 From: vladlosev Date: Wed, 14 Oct 2009 22:33:03 +0000 Subject: Fixes: Scons build file broken when used in another SConstruct; warning in VC 8.0 when compiled with /Wp64 --- scons/SConscript | 175 +++++++++++++++++++++++++----------------------- scons/SConscript.common | 140 ++++++++++++++++++++++++++++++++++++++ scons/SConstruct.common | 105 +---------------------------- src/gtest.cc | 3 +- 4 files changed, 235 insertions(+), 188 deletions(-) create mode 100644 scons/SConscript.common diff --git a/scons/SConscript b/scons/SConscript index 26fa5fb..60745f2 100644 --- a/scons/SConscript +++ b/scons/SConscript @@ -95,9 +95,13 @@ import os ############################################################ # Environments for building the targets, sorted by name. -Import('env', 'EnvCreator') +Import('env') +env = env.Clone() -env = EnvCreator.Create(env) +BUILD_TESTS = env.get('GTEST_BUILD_TESTS', False) +if BUILD_TESTS: + common_exports = SConscript('SConscript.common') + EnvCreator = common_exports['EnvCreator'] # Note: The relative paths in SConscript files are relative to the location # of the SConscript file itself. To make a path relative to the location of @@ -112,16 +116,17 @@ env = EnvCreator.Create(env) # file is one directory deeper than the gtest directory. env.Prepend(CPPPATH = ['..', '../include']) -env_use_own_tuple = EnvCreator.Create(env, EnvCreator.UseOwnTuple) -env_less_optimized = EnvCreator.Create(env, EnvCreator.LessOptimized) -env_with_threads = EnvCreator.Create(env, EnvCreator.WithThreads) -# The following environments are used to compile gtest_unittest.cc, which -# triggers a warning in all but the most recent GCC versions when compiling -# the EXPECT_EQ(NULL, ptr) statement. -env_warning_ok = EnvCreator.Create(env, EnvCreator.WarningOk) -env_with_exceptions = EnvCreator.Create(env_warning_ok, - EnvCreator.WithExceptions) -env_without_rtti = EnvCreator.Create(env_warning_ok, EnvCreator.NoRtti) +if BUILD_TESTS: + env_use_own_tuple = EnvCreator.Create(env, EnvCreator.UseOwnTuple) + env_less_optimized = EnvCreator.Create(env, EnvCreator.LessOptimized) + env_with_threads = EnvCreator.Create(env, EnvCreator.WithThreads) + # The following environments are used to compile gtest_unittest.cc, which + # triggers a warning in all but the most recent GCC versions when compiling + # the EXPECT_EQ(NULL, ptr) statement. + env_warning_ok = EnvCreator.Create(env, EnvCreator.WarningOk) + env_with_exceptions = EnvCreator.Create(env_warning_ok, + EnvCreator.WithExceptions) + env_without_rtti = EnvCreator.Create(env_warning_ok, EnvCreator.NoRtti) ############################################################ # Helpers for creating build targets. @@ -131,10 +136,14 @@ env_without_rtti = EnvCreator.Create(env_warning_ok, EnvCreator.NoRtti) # convenience. _all_objects = {} + +def GetObjSuffix(env): + return env.get('OBJ_SUFFIX', '') + def GtestObject(build_env, source): """Returns a target to build an object file from the given .cc source file.""" - object_name = os.path.basename(source).rstrip('.cc') + build_env['OBJ_SUFFIX'] + object_name = os.path.basename(source).rstrip('.cc') + GetObjSuffix(build_env) if object_name not in _all_objects: _all_objects[object_name] = build_env.Object(target=object_name, source=source) @@ -154,9 +163,9 @@ def GtestStaticLibraries(build_env): gtest_object = GtestObject(build_env, '../src/gtest-all.cc') gtest_main_object = GtestObject(build_env, '../src/gtest_main.cc') - return (build_env.StaticLibrary(target='gtest' + build_env['OBJ_SUFFIX'], + return (build_env.StaticLibrary(target='gtest' + GetObjSuffix(build_env), source=[gtest_object]), - build_env.StaticLibrary(target='gtest_main' + build_env['OBJ_SUFFIX'], + build_env.StaticLibrary(target='gtest_main' + GetObjSuffix(build_env), source=[gtest_object, gtest_main_object])) @@ -220,72 +229,68 @@ def GtestSample(build_env, target, additional_sources=None): # gtest_main.lib can be used if you just want a basic main function; it is also # used by some tests for Google Test itself. gtest, gtest_main = GtestStaticLibraries(env) -gtest_ex, gtest_main_ex = GtestStaticLibraries(env_with_exceptions) -gtest_no_rtti, gtest_main_no_rtti = GtestStaticLibraries(env_without_rtti) -gtest_use_own_tuple, gtest_use_own_tuple_main = GtestStaticLibraries( - env_use_own_tuple) +if BUILD_TESTS: + gtest_ex, gtest_main_ex = GtestStaticLibraries(env_with_exceptions) + gtest_no_rtti, gtest_main_no_rtti = GtestStaticLibraries(env_without_rtti) + gtest_use_own_tuple, gtest_use_own_tuple_main = GtestStaticLibraries( + env_use_own_tuple) # Install the libraries if needed. if 'LIB_OUTPUT' in env.Dictionary(): - env.Install('$LIB_OUTPUT', source=[gtest, gtest_main, - gtest_ex, gtest_main_ex, - gtest_no_rtti, gtest_main_no_rtti, - gtest_use_own_tuple, - gtest_use_own_tuple_main]) - -############################################################ -# Test targets using the standard environment. - -GtestTest(env, 'gtest-filepath_test', gtest_main) -GtestTest(env, 'gtest-message_test', gtest_main) -GtestTest(env, 'gtest-options_test', gtest_main) -GtestTest(env, 'gtest_environment_test', gtest) -GtestTest(env, 'gtest_main_unittest', gtest_main) -GtestTest(env, 'gtest_no_test_unittest', gtest) -GtestTest(env, 'gtest_pred_impl_unittest', gtest_main) -GtestTest(env, 'gtest_prod_test', gtest_main, - additional_sources=['../test/production.cc']) -GtestTest(env, 'gtest_repeat_test', gtest) -GtestTest(env, 'gtest_sole_header_test', gtest_main) -GtestTest(env, 'gtest-test-part_test', gtest_main) -GtestTest(env, 'gtest-typed-test_test', gtest_main, - additional_sources=['../test/gtest-typed-test2_test.cc']) -GtestTest(env, 'gtest-param-test_test', gtest, - additional_sources=['../test/gtest-param-test2_test.cc']) -GtestTest(env, 'gtest_color_test_', gtest) -GtestTest(env, 'gtest-linked_ptr_test', gtest_main) -GtestTest(env, 'gtest-port_test', gtest_main) -GtestTest(env, 'gtest_break_on_failure_unittest_', gtest) -GtestTest(env, 'gtest_filter_unittest_', gtest) -GtestTest(env, 'gtest_help_test_', gtest_main) -GtestTest(env, 'gtest_list_tests_unittest_', gtest) -GtestTest(env, 'gtest_throw_on_failure_test_', gtest) -GtestTest(env, 'gtest_xml_outfile1_test_', gtest_main) -GtestTest(env, 'gtest_xml_outfile2_test_', gtest_main) -GtestTest(env, 'gtest_xml_output_unittest_', gtest) -GtestTest(env, 'gtest-unittest-api_test', gtest) -GtestTest(env, 'gtest-listener_test', gtest) -GtestTest(env, 'gtest_shuffle_test_', gtest) - -############################################################ -# Tests targets using custom environments. - -GtestTest(env_warning_ok, 'gtest_unittest', gtest_main) -GtestTest(env_with_exceptions, 'gtest_output_test_', gtest_ex) -GtestTest(env_with_exceptions, 'gtest_throw_on_failure_ex_test', gtest_ex) -GtestTest(env_with_threads, 'gtest-death-test_test', gtest_main) -GtestTest(env_less_optimized, 'gtest_env_var_test_', gtest) -GtestTest(env_less_optimized, 'gtest_uninitialized_test_', gtest) -GtestTest(env_use_own_tuple, 'gtest-tuple_test', gtest_use_own_tuple_main) -GtestBinary(env_use_own_tuple, - 'gtest_use_own_tuple_test', - gtest_use_own_tuple_main, - ['../test/gtest-param-test_test.cc', - '../test/gtest-param-test2_test.cc']) -GtestBinary(env_with_exceptions, 'gtest_ex_unittest', gtest_main_ex, - ['../test/gtest_unittest.cc']) -GtestBinary(env_without_rtti, 'gtest_no_rtti_test', gtest_main_no_rtti, - ['../test/gtest_unittest.cc']) + env.Install('$LIB_OUTPUT', source=[gtest, gtest_main]) + +if BUILD_TESTS: + ############################################################ + # Test targets using the standard environment. + GtestTest(env, 'gtest-filepath_test', gtest_main) + GtestTest(env, 'gtest-message_test', gtest_main) + GtestTest(env, 'gtest-options_test', gtest_main) + GtestTest(env, 'gtest_environment_test', gtest) + GtestTest(env, 'gtest_main_unittest', gtest_main) + GtestTest(env, 'gtest_no_test_unittest', gtest) + GtestTest(env, 'gtest_pred_impl_unittest', gtest_main) + GtestTest(env, 'gtest_prod_test', gtest_main, + additional_sources=['../test/production.cc']) + GtestTest(env, 'gtest_repeat_test', gtest) + GtestTest(env, 'gtest_sole_header_test', gtest_main) + GtestTest(env, 'gtest-test-part_test', gtest_main) + GtestTest(env, 'gtest-typed-test_test', gtest_main, + additional_sources=['../test/gtest-typed-test2_test.cc']) + GtestTest(env, 'gtest-param-test_test', gtest, + additional_sources=['../test/gtest-param-test2_test.cc']) + GtestTest(env, 'gtest_color_test_', gtest) + GtestTest(env, 'gtest-linked_ptr_test', gtest_main) + GtestTest(env, 'gtest-port_test', gtest_main) + GtestTest(env, 'gtest_break_on_failure_unittest_', gtest) + GtestTest(env, 'gtest_filter_unittest_', gtest) + GtestTest(env, 'gtest_help_test_', gtest_main) + GtestTest(env, 'gtest_list_tests_unittest_', gtest) + GtestTest(env, 'gtest_throw_on_failure_test_', gtest) + GtestTest(env, 'gtest_xml_outfile1_test_', gtest_main) + GtestTest(env, 'gtest_xml_outfile2_test_', gtest_main) + GtestTest(env, 'gtest_xml_output_unittest_', gtest) + GtestTest(env, 'gtest-unittest-api_test', gtest) + GtestTest(env, 'gtest-listener_test', gtest) + GtestTest(env, 'gtest_shuffle_test_', gtest) + + ############################################################ + # Tests targets using custom environments. + GtestTest(env_warning_ok, 'gtest_unittest', gtest_main) + GtestTest(env_with_exceptions, 'gtest_output_test_', gtest_ex) + GtestTest(env_with_exceptions, 'gtest_throw_on_failure_ex_test', gtest_ex) + GtestTest(env_with_threads, 'gtest-death-test_test', gtest_main) + GtestTest(env_less_optimized, 'gtest_env_var_test_', gtest) + GtestTest(env_less_optimized, 'gtest_uninitialized_test_', gtest) + GtestTest(env_use_own_tuple, 'gtest-tuple_test', gtest_use_own_tuple_main) + GtestBinary(env_use_own_tuple, + 'gtest_use_own_tuple_test', + gtest_use_own_tuple_main, + ['../test/gtest-param-test_test.cc', + '../test/gtest-param-test2_test.cc']) + GtestBinary(env_with_exceptions, 'gtest_ex_unittest', gtest_main_ex, + ['../test/gtest_unittest.cc']) + GtestBinary(env_without_rtti, 'gtest_no_rtti_test', gtest_main_no_rtti, + ['../test/gtest_unittest.cc']) ############################################################ # Sample targets. @@ -312,14 +317,18 @@ if env.get('GTEST_BUILD_SAMPLES', False): GtestSample(env, 'sample9_unittest') GtestSample(env, 'sample10_unittest') -# These exports are used by Google Mock. gtest_exports = {'gtest': gtest, - 'gtest_ex': gtest_ex, - 'gtest_no_rtti': gtest_no_rtti, - 'gtest_use_own_tuple': gtest_use_own_tuple, - 'EnvCreator': EnvCreator, + 'gtest_main': gtest_main, + # These exports are used by Google Mock. 'GtestObject': GtestObject, 'GtestBinary': GtestBinary, 'GtestTest': GtestTest} + +if BUILD_TESTS: + # These environments are needed for tests only. + gtest_exports.update({'gtest_ex': gtest_ex, + 'gtest_no_rtti': gtest_no_rtti, + 'gtest_use_own_tuple': gtest_use_own_tuple}) + # Makes the gtest_exports dictionary available to the invoking SConstruct. Return('gtest_exports') diff --git a/scons/SConscript.common b/scons/SConscript.common new file mode 100644 index 0000000..a49cf0a --- /dev/null +++ b/scons/SConscript.common @@ -0,0 +1,140 @@ +# -*- Python -*- +# Copyright 2008 Google Inc. All Rights Reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions are +# met: +# +# * Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above +# copyright notice, this list of conditions and the following disclaimer +# in the documentation and/or other materials provided with the +# distribution. +# * Neither the name of Google Inc. nor the names of its +# contributors may be used to endorse or promote products derived from +# this software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +# Author: vladl@google.com (Vlad Losev) +# +# Shared SCons utilities for building Google Test's own tests. +# + +EnsurePythonVersion(2, 3) + + +class EnvCreator: + """Creates new customized environments from a base one.""" + + def _Remove(cls, env, attribute, value): + """Removes the given attribute value from the environment.""" + + attribute_values = env[attribute] + if value in attribute_values: + attribute_values.remove(value) + _Remove = classmethod(_Remove) + + def Create(cls, base_env, modifier=None): + # User should NOT create more than one environment with the same + # modifier (including None). + env = base_env.Clone() + if modifier: + modifier(env) + return env; + Create = classmethod(Create) + + # Each of the following methods modifies the environment for a particular + # purpose and can be used by clients for creating new environments. Each + # one needs to set the OBJ_SUFFIX variable to a unique suffix to + # differentiate targets built with that environment. Otherwise, SCons may + # complain about same target built with different settings. + + def UseOwnTuple(cls, env): + """Instructs Google Test to use its internal implementation of tuple.""" + + env['OBJ_SUFFIX'] = '_use_own_tuple' + env.Append(CPPDEFINES = 'GTEST_USE_OWN_TR1_TUPLE=1') + UseOwnTuple = classmethod(UseOwnTuple) + + def WarningOk(cls, env): + """Does not treat warnings as errors. + + Necessary for compiling gtest_unittest.cc, which triggers a gcc + warning when testing EXPECT_EQ(NULL, ptr).""" + + env['OBJ_SUFFIX'] = '_warning_ok' + if env['PLATFORM'] == 'win32': + cls._Remove(env, 'CCFLAGS', '-WX') + else: + cls._Remove(env, 'CCFLAGS', '-Werror') + WarningOk = classmethod(WarningOk) + + def WithExceptions(cls, env): + """Re-enables exceptions.""" + + env['OBJ_SUFFIX'] = '_ex' + if env['PLATFORM'] == 'win32': + env.Append(CCFLAGS=['/EHsc']) + env.Append(CPPDEFINES='_HAS_EXCEPTIONS=1') + # Undoes the _TYPEINFO_ hack, which is unnecessary and only creates + # trouble when exceptions are enabled. + cls._Remove(env, 'CPPDEFINES', '_TYPEINFO_') + cls._Remove(env, 'CPPDEFINES', '_HAS_EXCEPTIONS=0') + else: + env.Append(CCFLAGS='-fexceptions') + cls._Remove(env, 'CCFLAGS', '-fno-exceptions') + WithExceptions = classmethod(WithExceptions) + + def LessOptimized(cls, env): + """Disables certain optimizations on Windows. + + We need to disable some optimization flags for some tests on + Windows; otherwise the redirection of stdout does not work + (apparently because of a compiler bug).""" + + env['OBJ_SUFFIX'] = '_less_optimized' + if env['PLATFORM'] == 'win32': + for flag in ['/O1', '/Os', '/Og', '/Oy']: + cls._Remove(env, 'LINKFLAGS', flag) + LessOptimized = classmethod(LessOptimized) + + def WithThreads(cls, env): + """Allows use of threads. + + Currently only enables pthreads under GCC.""" + + env['OBJ_SUFFIX'] = '_with_threads' + if env['PLATFORM'] != 'win32': + # Assuming POSIX-like environment with GCC. + # TODO(vladl@google.com): sniff presence of pthread_atfork instead of + # selecting on a platform. + env.Append(CCFLAGS=['-pthread']) + env.Append(LINKFLAGS=['-pthread']) + WithThreads = classmethod(WithThreads) + + def NoRtti(cls, env): + """Disables RTTI support.""" + + env['OBJ_SUFFIX'] = '_no_rtti' + if env['PLATFORM'] == 'win32': + env.Append(CCFLAGS=['/GR-']) + else: + env.Append(CCFLAGS=['-fno-rtti']) + env.Append(CPPDEFINES='GTEST_HAS_RTTI=0') + NoRtti = classmethod(NoRtti) + + +sconscript_exports = {'EnvCreator': EnvCreator} +Return('sconscript_exports') diff --git a/scons/SConstruct.common b/scons/SConstruct.common index 2445beb..d9915b9 100644 --- a/scons/SConstruct.common +++ b/scons/SConstruct.common @@ -63,6 +63,7 @@ class SConstructHelper: vars.Add(ListVariable('BUILD', 'Build type', available_build_types[0], available_build_types)) vars.Add(BoolVariable('GTEST_BUILD_SAMPLES', 'Build samples', False)) + vars.Add(BoolVariable('GTEST_BUILD_TESTS', 'Build tests', True)) # Create base environment. self.env_base = Environment(variables=vars, @@ -82,108 +83,6 @@ class SConstructHelper: # Enable scons -h Help(vars.GenerateHelpText(self.env_base)) - class EnvCreator: - """Creates new customized environments from a base one.""" - - def _Remove(cls, env, attribute, value): - """Removes the given attribute value from the environment.""" - - attribute_values = env[attribute] - if value in attribute_values: - attribute_values.remove(value) - _Remove = classmethod(_Remove) - - def Create(cls, base_env, modifier=None): - # User should NOT create more than one environment with the same - # modifier (including None). - env = base_env.Clone() - if modifier: - modifier(env) - else: - env['OBJ_SUFFIX'] = '' # Default suffix for unchanged environment. - return env; - Create = classmethod(Create) - - # Each of the following methods modifies the environment for a particular - # purpose and can be used by clients for creating new environments. Each - # one needs to set the OBJ_SUFFIX variable to a unique suffix to - # differentiate targets built with that environment. Otherwise, SCons may - # complain about same target built with different settings. - - def UseOwnTuple(cls, env): - """Instructs Google Test to use its internal implementation of tuple.""" - - env['OBJ_SUFFIX'] = '_use_own_tuple' - env.Append(CPPDEFINES = 'GTEST_USE_OWN_TR1_TUPLE=1') - UseOwnTuple = classmethod(UseOwnTuple) - - def WarningOk(cls, env): - """Does not treat warnings as errors. - - Necessary for compiling gtest_unittest.cc, which triggers a gcc - warning when testing EXPECT_EQ(NULL, ptr).""" - - env['OBJ_SUFFIX'] = '_warning_ok' - if env['PLATFORM'] == 'win32': - cls._Remove(env, 'CCFLAGS', '-WX') - else: - cls._Remove(env, 'CCFLAGS', '-Werror') - WarningOk = classmethod(WarningOk) - - def WithExceptions(cls, env): - """Re-enables exceptions.""" - - env['OBJ_SUFFIX'] = '_ex' - if env['PLATFORM'] == 'win32': - env.Append(CCFLAGS=['/EHsc']) - env.Append(CPPDEFINES='_HAS_EXCEPTIONS=1') - # Undoes the _TYPEINFO_ hack, which is unnecessary and only creates - # trouble when exceptions are enabled. - cls._Remove(env, 'CPPDEFINES', '_TYPEINFO_') - cls._Remove(env, 'CPPDEFINES', '_HAS_EXCEPTIONS=0') - else: - env.Append(CCFLAGS='-fexceptions') - cls._Remove(env, 'CCFLAGS', '-fno-exceptions') - WithExceptions = classmethod(WithExceptions) - - def LessOptimized(cls, env): - """Disables certain optimizations on Windows. - - We need to disable some optimization flags for some tests on - Windows; otherwise the redirection of stdout does not work - (apparently because of a compiler bug).""" - - env['OBJ_SUFFIX'] = '_less_optimized' - if env['PLATFORM'] == 'win32': - for flag in ['/O1', '/Os', '/Og', '/Oy']: - cls._Remove(env, 'LINKFLAGS', flag) - LessOptimized = classmethod(LessOptimized) - - def WithThreads(cls, env): - """Allows use of threads. - - Currently only enables pthreads under GCC.""" - - env['OBJ_SUFFIX'] = '_with_threads' - if env['PLATFORM'] != 'win32': - # Assuming POSIX-like environment with GCC. - # TODO(vladl@google.com): sniff presence of pthread_atfork instead of - # selecting on a platform. - env.Append(CCFLAGS=['-pthread']) - env.Append(LINKFLAGS=['-pthread']) - WithThreads = classmethod(WithThreads) - - def NoRtti(cls, env): - """Disables RTTI support.""" - - env['OBJ_SUFFIX'] = '_no_rtti' - if env['PLATFORM'] == 'win32': - env.Append(CCFLAGS=['/GR-']) - else: - env.Append(CCFLAGS=['-fno-rtti']) - env.Append(CPPDEFINES='GTEST_HAS_RTTI=0') - NoRtti = classmethod(NoRtti) - def AllowVc71StlWithoutExceptions(self, env): env.Append( CPPDEFINES = [# needed for using some parts of STL with exception @@ -321,8 +220,6 @@ class SConstructHelper: self.SetBuildNameAndDir(gcc_opt, 'opt') def BuildSelectedEnvironments(self): - EnvCreator = SConstructHelper.EnvCreator - Export('EnvCreator') # Build using whichever environments the 'BUILD' option selected for build_name in self.env_base['BUILD']: print 'BUILDING %s' % build_name diff --git a/src/gtest.cc b/src/gtest.cc index 9340724..55f03ce 100644 --- a/src/gtest.cc +++ b/src/gtest.cc @@ -3170,7 +3170,8 @@ void XmlUnitTestResultPrinter::OutputXmlCDataSection(::std::ostream* stream, for (;;) { const char* const next_segment = strstr(segment, "]]>"); if (next_segment != NULL) { - stream->write(segment, next_segment - segment); + stream->write( + segment, static_cast(next_segment - segment)); *stream << "]]>]]>"); } else { -- cgit v0.12