Boost logo

Boost-Commit :

Subject: [Boost-commit] svn:boost r73432 - in sandbox/tools/profile_templates2: . doc
From: dsaritz_at_[hidden]
Date: 2011-07-29 11:25:05


Author: psiha
Date: 2011-07-29 11:25:04 EDT (Fri, 29 Jul 2011)
New Revision: 73432
URL: http://svn.boost.org/trac/boost/changeset/73432

Log:
Added a basic readme.
Reimplemented preprocess.pl in C++ with Xpressive.
Replaced the main BB jam file with a CMake module.
Added:
   sandbox/tools/profile_templates2/doc/readme.txt (contents, props changed)
   sandbox/tools/profile_templates2/preprocess.cpp
      - copied, changed from r73430, /sandbox/tools/profile_templates2/preprocess.pl
   sandbox/tools/profile_templates2/profiler.cmake (contents, props changed)
Removed:
   sandbox/tools/profile_templates2/preprocess.pl
   sandbox/tools/profile_templates2/template-profile.jam
Text files modified:
   sandbox/tools/profile_templates2/preprocess.cpp | 258 +++++++++++++++++++++++++++++++--------
   1 files changed, 202 insertions(+), 56 deletions(-)

Added: sandbox/tools/profile_templates2/doc/readme.txt
==============================================================================
--- (empty file)
+++ sandbox/tools/profile_templates2/doc/readme.txt 2011-07-29 11:25:04 EDT (Fri, 29 Jul 2011)
@@ -0,0 +1,7 @@
+A rework of the SW's original with the following goals:
+ - remove dependencies on Perl and a built Boost (Regex) by moving to Boost.Xpressive and later to Boost.Spirit
+ - further improve performance (e.g. low level C IO and memory mapped files instead of C++ streams)
+ - convert to a single standalone binary
+ - move to CMake and support for creating profiling targets in user projects/solutions.
+
+ (...work in progress...)
\ No newline at end of file

Copied: sandbox/tools/profile_templates2/preprocess.cpp (from r73430, /sandbox/tools/profile_templates2/preprocess.pl)
==============================================================================
--- /sandbox/tools/profile_templates2/preprocess.pl (original)
+++ sandbox/tools/profile_templates2/preprocess.cpp 2011-07-29 11:25:04 EDT (Fri, 29 Jul 2011)
@@ -1,60 +1,206 @@
-# preprocess.pl
-#
-# Copyright (c) 2008-2009
-# Steven Watanabe
-#
-# Distributed under the Boost Software License, Version 1.0. (See
-# accompanying file LICENSE_1_0.txt or copy at
-# http://www.boost.org/LICENSE_1_0.txt)
-
-#add "~" to the end of the backup file name
-$^I = "~";
-
-#read the whole file at once
-undef $/;
-use re 'eval' ;
-
-$backslashed_lines = qr/(?>(?>\\(?>\n|\r\n)|.)*)/;
-$string = qr/(?>\"(?>\\\\|\\\"|[^\"])*\"|'(?>\\\\|\\'|[^'])*')/;
-$comment = qr{(?>//$backslashed_lines|/\*(?>[^*]|\*(?!/))*\*/)};
-$pp = qr/(?>#$backslashed_lines)/;
-$ignored = qr/(?>$string|$comment|$pp)/;
-$parens = qr/(?>\((?>(?>(?>$ignored|[^()])+)|(??{$parens}))*\))/;
-$ws = qr/(?:$comment|$pp|\s|(?:\\(?:\n|\r\n)))/;
-
-$class_header = qr/(?>(?>\b(?:class|struct))(?>$ws+\w+)(?>(?>[^(){;=]|$parens|$ignored)*)\{)/;
-
-$control = qr/(?:\b(?:__attribute__|__if_exists|__if_not_exists|for|while|if|catch|switch)\b)/;
-$modifiers = qr/(?:\b(?:try|const|volatile)\b)/;
-$start = qr/(?:^|\G|(?<=[{};]))(?>$ws*)/;
-$body = qr/(?:(?!$control)(?>$ignored|[^{};]))/;
-$end = qr/(?:$parens|\])/;
-$body_start = qr/(?>$ws*(?:$modifiers$ws*)*\{)/;
-
-$function_header = qr/(?>(?:$start)(?:$body*?$end)(?:$body_start))/;
-
-_at_braces = ();
-
-sub process {
- my $header = $_[0];
- my $open_brace = $_[1];
- my $close_brace = $_[2];
-
- if($header) {
- push(@braces, " TEMPLATE_PROFILE_EXIT() }");
- return("$header TEMPLATE_PROFILE_ENTER()");
- } elsif($open_brace) {
- push(@braces, "}");
- return($open_brace);
- } elsif($close_brace) {
- return(pop(@braces));
- } else {
- die("This should only be called if the pattern matched: \$$_[0],$_[1],$_[2],$_[3],\$");
+////////////////////////////////////////////////////////////////////////////////
+///
+/// \file preprocess.cpp
+/// --------------------
+///
+/// Copyright (c) 2008.-2009. Steven Watanabe (preprocess.pl)
+/// Copyright (c) 2011. Domagoj Saric
+///
+/// Use, modification and distribution is subject to the
+/// Boost Software License, Version 1.0.
+/// (See accompanying file LICENSE_1_0.txt or copy at
+/// http://www.boost.org/LICENSE_1_0.txt)
+///
+/// For more information, see http://www.boost.org
+///
+////////////////////////////////////////////////////////////////////////////////
+//------------------------------------------------------------------------------
+#undef BOOST_ENABLE_ASSERT_HANDLER
+
+#define BOOST_XPRESSIVE_USE_C_TRAITS
+
+#include "boost/assert.hpp"
+#include "boost/concept_check.hpp"
+#include "boost/interprocess/file_mapping.hpp"
+#include "boost/interprocess/mapped_region.hpp"
+#include "boost/range/iterator_range_core.hpp"
+#include "boost/xpressive/xpressive.hpp"
+
+#include <cassert>
+#include <iterator>
+#include <iostream>
+#include <fstream>
+//------------------------------------------------------------------------------
+
+namespace regex
+{
+ using namespace boost::xpressive;
+
+ cregex make_parens()
+ {
+ cregex parens;// parens = keep( '(' >> *keep( keep( +keep( ignored | ~(set= '(',')') ) | ( -!by_ref( parens ) ) ) ) >> ')' );
+ parens =
+ '(' // is an opening parenthesis ...
+ >> // followed by ...
+ *( // zero or more ...
+ keep( +~(set='(',')') ) // of a bunch of things that are not parentheses ...
+ | // or ...
+ by_ref(parens) // a balanced set of parentheses
+ ) // (ooh, recursion!) ...
+ >> // followed by ...
+ ')' // a closing parenthesis
+ ;
+ return parens;
     }
+
+ cregex const backslashed_lines = keep( keep( *( '\\' >> keep( _ln ) | _ ) ) );
+ cregex const string = cregex::compile( "(?>\"(?>\\\\|\\\"|[^\"])*\"|'(?>\\\\|\\'|[^'])*')" );
+ cregex const comment = keep( "//" >> backslashed_lines | "/*" >> keep( *( ~(set='*') | '*' >> ~before('/') ) ) >> "*/" );
+ cregex const pp = keep( '#' >> backslashed_lines );
+ cregex const ignored = keep( string | comment | pp );
+ cregex const parens = make_parens();
+ cregex const ws = comment | pp | _s | _ln;
+
+ cregex const class_header = keep( keep( _b >> ( as_xpr( "class" ) | "struct" ) ) >> keep( +ws >> +_w ) >> keep( *keep( ~(set= '(',')','{',';','=') | parens | ignored ) ) >> '{' );
+
+ cregex const control = ( _b >> ( as_xpr( "__attribute__" ) | "__if_exists" | "__if_not_exists" | "for" | "while" | "if" | "catch" | "switch" ) >> _b );
+ cregex const modifiers = ( _b >> ( as_xpr( "try" ) | "const" | "volatile" ) >> _b );
+ cregex const start = ( bos /*| cregex::compile( "\\G" )*/ | after( (set= '{','}',';') ) ) >> keep( *ws );
+ cregex const body = ~before( control ) >> keep( ignored | ~(set= '{','}',';') );
+ cregex const end = parens | ']';
+ cregex const body_start = keep( *ws >> *(modifiers >> *ws) >> '{' );
+
+ cregex const function_header = keep( start >> ( *body >> end ) >> body_start );
 }
 
-while(<>) {
- s/(($ignored)|((?>$class_header|$function_header))|([{])|([}]))/$2?$2:process($3,$4,$5)/ge;
- print "#include <template_profiler.hpp>\n";
- print;
+struct formatter : boost::noncopyable
+{
+ template<typename Out>
+ Out operator()( regex::cmatch const & what, Out out ) const
+ {
+ using namespace regex;
+
+ typedef cmatch::value_type sub_match;
+
+ BOOST_ASSERT( what.size() == 5 );
+
+ cmatch::const_iterator const p_match( std::find_if( what.begin() + 1, what.end(), []( sub_match const & match ){ return match.matched; } ) );
+ BOOST_ASSERT_MSG( p_match != what.end(), "Something should have matched." );
+ sub_match const & match( *p_match );
+
+ enum match_type_t
+ {
+ ignore = 1,
+ header,
+ open_brace,
+ close_brace
+ };
+
+ unsigned int const match_type( p_match - what.begin() );
+ switch ( match_type )
+ {
+ case ignore:
+ out = std::copy( match.first, match.second, out );
+ break;
+
+ case header:
+ {
+ braces.push_back( " TEMPLATE_PROFILE_EXIT() }" );
+ static char const tail[] = " TEMPLATE_PROFILE_ENTER()";
+ out = std::copy( match.first , match.second , out );
+ out = std::copy( boost::begin( tail ), boost::end( tail ) - 1, out );
+ break;
+ }
+
+ case open_brace:
+ braces.push_back( "}" );
+ out = std::copy( match.first, match.second, out );
+ break;
+
+ case close_brace:
+ out = std::copy( braces.back().begin(), braces.back().end(), out );
+ braces.pop_back();
+ break;
+
+ default:
+ BOOST_ASSERT( false );
+ break;
+ }
+
+ if ( match_type != header )
+ {
+ //...zzz...definitions where the opening brace is on the next line are not getting caught...
+ static char const class_ [] = "class";
+ static char const struct_[] = "struct";
+ BOOST_ASSERT( std::find_end( match.first, match.second, boost::begin( class_ ), boost::end( class_ ) - 1 ) == match.second );
+ BOOST_ASSERT( std::find_end( match.first, match.second, boost::begin( struct_ ), boost::end( struct_ ) - 1 ) == match.second );
+ std::string const mstr( match.str() );
+ BOOST_ASSERT( !std::strstr( mstr.c_str(), class_ ) );
+ BOOST_ASSERT( !std::strstr( mstr.c_str(), struct_ ) );
+ }
+
+ return out;
+ }
+
+ mutable std::vector<std::string> braces;
+};
+
+
+int main( int const argc, char * * const argv )
+{
+ if ( argc != 2 )
+ return EXIT_FAILURE;
+
+ try
+ {
+ using namespace boost;
+
+ interprocess::mapped_region const input_file_view
+ (
+ interprocess::file_mapping
+ (
+ argv[ 1 ],
+ interprocess::read_only
+ ),
+ interprocess::read_only
+ );
+
+ iterator_range<char const *> input
+ (
+ static_cast<char const *>( input_file_view.get_address() ),
+ static_cast<char const *>( input_file_view.get_address() ) + input_file_view.get_size()
+ );
+
+ using namespace regex;
+ cregex const main_regex( (s1= ignored) | (s2=keep( class_header | function_header )) | (s3='{') | (s4='}') );
+ match_results<char const *> search_results;
+
+ std::ofstream output( "preprocessed.cpp" );
+ output << "#include <template_profiler.hpp>\n" << std::endl;
+ std::ostream_iterator<char> out_iter( output );
+
+ formatter fmt;
+
+ while ( input.begin() < input.end() )
+ {
+ char const * /*const*/ p_endl( std::find( input.begin(), input.end(), '\n' ) );
+ std::size_t const line_length( p_endl - input.begin() );
+
+ out_iter = regex_replace( out_iter, input.begin(), p_endl, main_regex, fmt );
+
+ *out_iter++ = *p_endl++;
+ input = iterator_range<char const *>( p_endl, input.end() );
+ }
+
+ return EXIT_SUCCESS;
+ }
+ catch ( std::exception const & e )
+ {
+ std::puts( e.what() );
+ return EXIT_FAILURE;
+ }
+ catch ( ... )
+ {
+ return EXIT_FAILURE;
+ }
 }

Deleted: sandbox/tools/profile_templates2/preprocess.pl
==============================================================================
--- sandbox/tools/profile_templates2/preprocess.pl 2011-07-29 11:25:04 EDT (Fri, 29 Jul 2011)
+++ (empty file)
@@ -1,60 +0,0 @@
-# preprocess.pl
-#
-# Copyright (c) 2008-2009
-# Steven Watanabe
-#
-# Distributed under the Boost Software License, Version 1.0. (See
-# accompanying file LICENSE_1_0.txt or copy at
-# http://www.boost.org/LICENSE_1_0.txt)
-
-#add "~" to the end of the backup file name
-$^I = "~";
-
-#read the whole file at once
-undef $/;
-use re 'eval' ;
-
-$backslashed_lines = qr/(?>(?>\\(?>\n|\r\n)|.)*)/;
-$string = qr/(?>\"(?>\\\\|\\\"|[^\"])*\"|'(?>\\\\|\\'|[^'])*')/;
-$comment = qr{(?>//$backslashed_lines|/\*(?>[^*]|\*(?!/))*\*/)};
-$pp = qr/(?>#$backslashed_lines)/;
-$ignored = qr/(?>$string|$comment|$pp)/;
-$parens = qr/(?>\((?>(?>(?>$ignored|[^()])+)|(??{$parens}))*\))/;
-$ws = qr/(?:$comment|$pp|\s|(?:\\(?:\n|\r\n)))/;
-
-$class_header = qr/(?>(?>\b(?:class|struct))(?>$ws+\w+)(?>(?>[^(){;=]|$parens|$ignored)*)\{)/;
-
-$control = qr/(?:\b(?:__attribute__|__if_exists|__if_not_exists|for|while|if|catch|switch)\b)/;
-$modifiers = qr/(?:\b(?:try|const|volatile)\b)/;
-$start = qr/(?:^|\G|(?<=[{};]))(?>$ws*)/;
-$body = qr/(?:(?!$control)(?>$ignored|[^{};]))/;
-$end = qr/(?:$parens|\])/;
-$body_start = qr/(?>$ws*(?:$modifiers$ws*)*\{)/;
-
-$function_header = qr/(?>(?:$start)(?:$body*?$end)(?:$body_start))/;
-
-_at_braces = ();
-
-sub process {
- my $header = $_[0];
- my $open_brace = $_[1];
- my $close_brace = $_[2];
-
- if($header) {
- push(@braces, " TEMPLATE_PROFILE_EXIT() }");
- return("$header TEMPLATE_PROFILE_ENTER()");
- } elsif($open_brace) {
- push(@braces, "}");
- return($open_brace);
- } elsif($close_brace) {
- return(pop(@braces));
- } else {
- die("This should only be called if the pattern matched: \$$_[0],$_[1],$_[2],$_[3],\$");
- }
-}
-
-while(<>) {
- s/(($ignored)|((?>$class_header|$function_header))|([{])|([}]))/$2?$2:process($3,$4,$5)/ge;
- print "#include <template_profiler.hpp>\n";
- print;
-}

Added: sandbox/tools/profile_templates2/profiler.cmake
==============================================================================
--- (empty file)
+++ sandbox/tools/profile_templates2/profiler.cmake 2011-07-29 11:25:04 EDT (Fri, 29 Jul 2011)
@@ -0,0 +1,64 @@
+################################################################################
+# Copyright 2003 & onward LASMEA UMR 6602 CNRS/Univ. Clermont II
+# Copyright 2009 & onward LRI UMR 8623 CNRS/Univ Paris Sud XI
+# Copyright 2011 & onward Domagoj Saric
+#
+# Based on the original from the NT2 library.
+# (https://github.com/MetaScale/nt2)
+#
+# Distributed under the Boost Software License, Version 1.0.
+# See accompanying file LICENSE.txt or copy at
+# http://www.boost.org/LICENSE_1_0.txt
+################################################################################
+
+################################################################################
+# Add the target to build filter and postprocess
+################################################################################
+FIND_FILE(PROFILER_PATH profiler ${CMAKE_MODULE_PATH})
+
+ADD_EXECUTABLE(template.profiler.filter ${PROFILER_PATH}/filter.cpp)
+set_property(TARGET template.profiler.filter PROPERTY RUNTIME_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/tools)
+
+INCLUDE_DIRECTORIES(${Boost_INCLUDE_DIRS})
+ADD_EXECUTABLE(template.profiler.postprocess ${PROFILER_PATH}/postprocess.cpp)
+if (NOT MSVC)
+ target_link_libraries(template.profiler.postprocess ${Boost_LIBRARIES})
+endif()
+set_property(TARGET template.profiler.postprocess PROPERTY RUNTIME_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/tools)
+
+################################################################################
+# Make a function to compile foo and profile it
+################################################################################
+function(template_profile target src)
+ if(CMAKE_GENERATOR MATCHES "Make")
+ set( profiler_cxx_flags ${CMAKE_CXX_FLAGS_${CMAKE_BUILD_TYPE}} )
+ else()
+ set( profiler_cxx_flags ${CMAKE_CXX_FLAGS_DEBUG} )
+ endif()
+
+ get_directory_property( preprocessor_definitions COMPILE_DEFINITIONS )
+ foreach(preprocessor_definition ${preprocessor_definitions})
+ list(APPEND profiler_cxx_flags -D${preprocessor_definition})
+ endforeach()
+
+ get_directory_property(INCLUDES INCLUDE_DIRECTORIES)
+ foreach(INCLUDE ${INCLUDES})
+ list(APPEND INCLUDE_DIRECTORIES -I"${INCLUDE}")
+ endforeach()
+
+ add_custom_command(OUTPUT ${target}.preprocessed.cpp
+ COMMAND ${CMAKE_CXX_COMPILER} ${profiler_cxx_flags} ${INCLUDE_DIRECTORIES} -E ${CMAKE_CURRENT_SOURCE_DIR}/${src}
+ | ${PERL_EXECUTABLE} ${PROFILER_PATH}/preprocess.pl > ${target}.preprocessed.cpp
+ DEPENDS ${src}
+ )
+ add_custom_command(OUTPUT ${target}.template_profile
+ COMMAND ${CMAKE_CXX_COMPILER} ${profiler_cxx_flags} -I${PROFILER_PATH} ${INCLUDE_DIRECTORIES} -c -DPROFILE_TEMPLATES ${target}.preprocessed.cpp 2>&1
+ | \"${PROJECT_BINARY_DIR}/tools/${CMAKE_CFG_INTDIR}/template.profiler.filter\" ${ARGN} > ${target}.filtered && \"${PROJECT_BINARY_DIR}/tools/${CMAKE_CFG_INTDIR}/template.profiler.postprocess\" ${ARGN} ${target}.filtered > ${target}.template_profile
+ DEPENDS ${target}.preprocessed.cpp
+ template.profiler.filter
+ template.profiler.postprocess
+ )
+ add_custom_target (${target}
+ DEPENDS ${target}.template_profile
+ )
+endfunction()

Deleted: sandbox/tools/profile_templates2/template-profile.jam
==============================================================================
--- sandbox/tools/profile_templates2/template-profile.jam 2011-07-29 11:25:04 EDT (Fri, 29 Jul 2011)
+++ (empty file)
@@ -1,178 +0,0 @@
-# template-profile.jam
-#
-# Copyright (c) 2008
-# Steven Watanabe
-#
-# Distributed under the Boost Software License, Version 1.0. (See
-# accompanying file LICENSE_1_0.txt or copy at
-# http://www.boost.org/LICENSE_1_0.txt)
-
-import feature ;
-import toolset ;
-import type ;
-import errors ;
-import path ;
-import modules ;
-import generators ;
-import "class" ;
-
-module-location = [ path.parent [ path.make [ modules.binding template-profile ] ] ] ;
-
-INSTRUMENT-ACTION = [ path.native [ path.join $(module-location) preprocess.pl ] ] ;
-INSTRUMENT-ACTION = perl \"$(INSTRUMENT-ACTION)\" ;
-
-type.register INSTRUMENTED_TEMPLATE_PREPROCESSED_CPP : : CPP ;
-type.register RAW_TEMPLATE_PROFILE : rtp ;
-type.register TEMPLATE_PROFILE : template-profile ;
-
-feature.feature <template-profile-toolset> : msvc gcc : free ;
-feature.feature <template-profile-filter> : : path incidental ;
-feature.feature <flat-profile> : on off : incidental propagated ;
-feature.feature <call-graph> : on off : incidental propagated ;
-
-rule init-toolset ( toolset ) {
- toolset.flags $(toolset).compile.c++.preprocess INSTRUMENT-ACTION : $(INSTRUMENT-ACTION) : unchecked ;
- toolset.flags $(toolset).compile.c++.template-profile FILTER <template-profile-filter> : : unchecked ;
- toolset.flags $(toolset).compile.c++.template-profile FILTER-OPTIONS <call-graph>on : --call-graph : unchecked ;
- generators.register-c-compiler $(toolset).compile.c++.preprocess : CPP : INSTRUMENTED_TEMPLATE_PREPROCESSED_CPP : <toolset>$(toolset) ;
-}
-
-module gcc {
-
- import template-profile : init-toolset ;
-
- template-profile.init-toolset gcc ;
-
- actions compile.c++.preprocess {
- $(CONFIG_COMMAND) $(OPTIONS) $(USER_OPTIONS) -D$(DEFINES) -I"$(INCLUDES)" -E "$(>)" | $(INSTRUMENT-ACTION) >"$(<)"
- }
-
- actions compile.c++.template-profile {
- "$(CONFIG_COMMAND)" $(LANG) -ftemplate-depth-$(TEMPLATE_DEPTH) $(OPTIONS) $(USER_OPTIONS) -D$(DEFINES) -D PROFILE_TEMPLATES -I"$(INCLUDES)" -c "$(>:W)" 2>&1 | "$(FILTER)" $(FILTER-OPTIONS) >"$(<)"
- }
-
-}
-
-module msvc {
-
- import template-profile : init-toolset ;
- template-profile.init-toolset msvc ;
-
- actions compile.c++.preprocess {
- $(.CC) @"@($(<[1]:W).rsp:E="$(>[1]:W)" -E $(lang-opt) -U$(UNDEFS) $(CFLAGS) $(C++FLAGS) $(OPTIONS) $(.nl)-D$(DEFINES) $(.nl)"-I$(INCLUDES:W)")" | $(INSTRUMENT-ACTION) >"$(<[1]:W)"
- }
-
- actions compile.c++.template-profile {
- $(.CC) @"@($(<[1]:W).rsp:E="$(>[1]:W)" -c $(lang-opt) -U$(UNDEFS) $(CFLAGS) $(C++FLAGS) $(OPTIONS) -W4 $(.nl)-D$(DEFINES) -D PROFILE_TEMPLATES $(.nl)"-I$(INCLUDES:W)")" 2>&1 | "$(FILTER)" $(FILTER-OPTIONS) >"$(<)"
- }
-
-}
-
-class warn-generator : generator {
-
- import template-profile ;
- import targets ;
- import path ;
- import modules ;
-
- rule __init__ ( * : * ) {
- generator.__init__ $(1) : $(2) : $(3) : $(4) : $(5) : $(6) : $(7) : $(8) : $(9) ;
- }
- rule run ( project name : properties : sources * : multiple ? ) {
- local toolset = [ $(properties).get <toolset> ] ;
- if ! $(toolset) {
- errors.error "No toolset specified" ;
- }
- switch $(toolset) {
- case msvc* :
- toolset = msvc ;
- case gcc* :
- toolset = gcc ;
- case * :
- errors.error unrecognized toolset $(toolset) ;
- }
- local self-dir = [ modules.peek template-profile : module-location ] ;
-
- current_path = [ modules.peek template-profile : module-location ] ;
- local filter-main-target = [ targets.resolve-reference [ path.join $(current_path) src ] : $(project) ] ;
- filter-main-target = [ $(filter-main-target[1]).main-target filter ] ;
- local filter-binary-dependencies = [ $(filter-main-target).generate [ $(properties).propagated ] ] ;
- filter-binary-dependencies = $(filter-binary-dependencies[2-]) ;
- local filter-binary = ;
-
- for local target in $(filter-binary-dependencies) {
- if [ $(target).type ] = EXE {
- filter-binary =
- [ path.native
- [ path.join
- [ $(target).path ]
- [ $(target).name ]
- ]
- ] ;
- }
- }
-
- if ! $(filter-binary) {
- errors.error Could not find filter binary ;
- }
-
- local new-properties = [ $(properties).add-raw <dependency>$(filter-binary-dependencies) <template-profile-filter>$(filter-binary) <include>$(self-dir) ] ;
-
- return [ generator.run $(project) $(name) : $(new-properties) : $(sources) : $(multiple) ] ;
- }
-}
-
-generators.register [ class.new warn-generator msvc.compile.c++.template-profile : INSTRUMENTED_TEMPLATE_PREPROCESSED_CPP : RAW_TEMPLATE_PROFILE : <toolset>msvc ] ;
-generators.register [ class.new warn-generator gcc.compile.c++.template-profile : INSTRUMENTED_TEMPLATE_PREPROCESSED_CPP : RAW_TEMPLATE_PROFILE : <toolset>gcc ] ;
-
-class final-profile-generator : generator {
-
- import targets ;
- import template-profile ;
- import path ;
- import modules ;
-
- rule __init__ ( ) {
- generator.__init__ template-profile.process-raw-profile : RAW_TEMPLATE_PROFILE : TEMPLATE_PROFILE ;
- }
- rule run ( project name : properties : sources * : multiple ? ) {
-
- current_path = [ modules.peek template-profile : module-location ] ;
-
- local postprocess-main-target = [ targets.resolve-reference [ path.join $(current_path) src ] : $(project) ] ;
- postprocess-main-target = [ $(postprocess-main-target[1]).main-target postprocess ] ;
- local postprocess-binary-dependencies = [ $(postprocess-main-target).generate [ $(properties).propagated ] ] ;
- postprocess-binary-dependencies = $(postprocess-binary-dependencies[2-]) ;
- local postprocess-binary = ;
-
- for local target in $(postprocess-binary-dependencies) {
- if [ $(target).type ] = EXE {
- postprocess-binary =
- [ path.native
- [ path.join
- [ $(target).path ]
- [ $(target).name ]
- ]
- ] ;
- }
- }
-
- if ! $(postprocess-binary) {
- errors.error Could not find postprocessor binary ;
- }
-
- local new-properties = [ $(properties).add-raw <dependency>$(postprocess-binary-dependencies) <postprocess-binary>$(postprocess-binary) ] ;
- return [ generator.run $(project) $(name) : $(new-properties) : $(sources) : $(multiple) ] ;
- }
-}
-
-generators.register [ class.new final-profile-generator ] ;
-
-feature.feature <postprocess-binary> : : path incidental ;
-
-toolset.flags template-profile.process-raw-profile POSTPROCESS-BINARY <postprocess-binary> ;
-toolset.flags template-profile.process-raw-profile POSTPROCESS-OPTIONS <call-graph>on : --call-graph ;
-
-actions process-raw-profile {
- "$(POSTPROCESS-BINARY)" $(POSTPROCESS-OPTIONS) "$(>)" >"$(<)"
-}


Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk