Boost logo

Boost-Commit :

Subject: [Boost-commit] svn:boost r65203 - in branches/quickbook-1.5-spirit2: . src test
From: dnljms_at_[hidden]
Date: 2010-09-02 18:40:32


Author: danieljames
Date: 2010-09-02 18:40:31 EDT (Thu, 02 Sep 2010)
New Revision: 65203
URL: http://svn.boost.org/trac/boost/changeset/65203

Log:
Merge optimization for stacking macros.

It turns out the spirit 2 version didn't have the speed problem because the
spirit 2 macro copy constructs by reference. But this also meant that scoping
wasn't working properly. So this fixes that, but probably makes this slower.
Especially since gcc can't cope with a symbol table stored directly in a
container (because it tries to use `&` to take its address).

Added:
   branches/quickbook-1.5-spirit2/test/macro.gold
      - copied unchanged from r65102, /trunk/tools/quickbook/test/macro.gold
   branches/quickbook-1.5-spirit2/test/macro.quickbook
      - copied unchanged from r65102, /trunk/tools/quickbook/test/macro.quickbook
Properties modified:
   branches/quickbook-1.5-spirit2/ (props changed)
Text files modified:
   branches/quickbook-1.5-spirit2/src/block_actions.cpp | 3 +++
   branches/quickbook-1.5-spirit2/src/state.cpp | 25 +++++++++++++++++++++++--
   branches/quickbook-1.5-spirit2/src/state.hpp | 18 +++++++++++++++++-
   branches/quickbook-1.5-spirit2/test/Jamfile.v2 | 1 +
   4 files changed, 44 insertions(+), 3 deletions(-)

Modified: branches/quickbook-1.5-spirit2/src/block_actions.cpp
==============================================================================
--- branches/quickbook-1.5-spirit2/src/block_actions.cpp (original)
+++ branches/quickbook-1.5-spirit2/src/block_actions.cpp 2010-09-02 18:40:31 EDT (Thu, 02 Sep 2010)
@@ -168,6 +168,7 @@
     {
         state.paragraph_output();
 
+ state.copy_macros_for_write();
         state.macro.add(
             x.macro_identifier.begin()
           , x.macro_identifier.end()
@@ -361,6 +362,7 @@
 
         // scope the macros
         macro_symbols macro = state.macro;
+ std::size_t macro_change_depth = state.macro_change_depth;
         // scope the templates
         //~ template_symbols templates = state.templates; $$$ fixme $$$
 
@@ -389,6 +391,7 @@
 
         // restore the macros
         state.macro = macro;
+ state.macro_change_depth = macro_change_depth;
         // restore the templates
         //~ state.templates = templates; $$$ fixme $$$
     }

Modified: branches/quickbook-1.5-spirit2/src/state.cpp
==============================================================================
--- branches/quickbook-1.5-spirit2/src/state.cpp (original)
+++ branches/quickbook-1.5-spirit2/src/state.cpp 2010-09-02 18:40:31 EDT (Thu, 02 Sep 2010)
@@ -37,6 +37,7 @@
     // state
         , filename(fs::absolute(fs::path(filein_)))
         , outdir(outdir_)
+ , macro_change_depth(0)
         , macro()
         , section_level(0)
         , min_section_level(0)
@@ -66,7 +67,7 @@
     {
         state_stack.push(
             boost::make_tuple(
- macro
+ macro_change_depth
               , section_level
               , min_section_level
               , section_id
@@ -79,11 +80,31 @@
         block.push();
         templates.push();
     }
+
+ // Pushing and popping the macro symbol table is pretty expensive, so
+ // instead implement a sort of 'stack on write'. Call this whenever a
+ // change is made to the macro table, and it'll stack the current macros
+ // if necessary. Would probably be better to implement macros in a less
+ // expensive manner.
+ void state::copy_macros_for_write()
+ {
+ if(macro_change_depth != state_stack.size())
+ {
+ macro_stack.push(macro_symbols_wrap(macro));
+ macro_change_depth = state_stack.size();
+ }
+ }
 
     void state::pop()
     {
+ if(macro_change_depth == state_stack.size())
+ {
+ macro = macro_stack.top().get();
+ macro_stack.pop();
+ }
+
         boost::tie(
- macro
+ macro_change_depth
           , section_level
           , min_section_level
           , section_id

Modified: branches/quickbook-1.5-spirit2/src/state.hpp
==============================================================================
--- branches/quickbook-1.5-spirit2/src/state.hpp (original)
+++ branches/quickbook-1.5-spirit2/src/state.hpp 2010-09-02 18:40:31 EDT (Thu, 02 Sep 2010)
@@ -50,6 +50,7 @@
         fs::path filename;
 
     // scope state
+ std::size_t macro_change_depth;
         macro_symbols macro;
         int section_level;
         int min_section_level;
@@ -58,15 +59,29 @@
         std::string source_mode;
 
         typedef boost::tuple<
- macro_symbols
+ std::size_t
           , int
           , int
           , raw_string
           , raw_string
           , std::string>
         state_tuple;
+
+ // Can't store macro_symbols directly in a container on gcc, because
+ // proto overloads operator&.
+ struct macro_symbols_wrap {
+ macro_symbols_wrap() : symbols() {}
+ explicit macro_symbols_wrap(macro_symbols const& x) : symbols() {
+ symbols = x;
+ }
+ macro_symbols const& get() const { return symbols; }
+
+ macro_symbols symbols;
+ };
 
         std::stack<state_tuple> state_stack;
+ // Stack macros separately as copying macros is expensive
+ std::stack<macro_symbols_wrap> macro_stack;
 
     // temporary or global state
         int template_depth;
@@ -74,6 +89,7 @@
         int error_count;
 
     // push/pop the states and the streams
+ void copy_macros_for_write();
         void push();
         void pop();
 

Modified: branches/quickbook-1.5-spirit2/test/Jamfile.v2
==============================================================================
--- branches/quickbook-1.5-spirit2/test/Jamfile.v2 (original)
+++ branches/quickbook-1.5-spirit2/test/Jamfile.v2 2010-09-02 18:40:31 EDT (Thu, 02 Sep 2010)
@@ -45,6 +45,7 @@
     [ quickbook-test image_1_5 ]
     [ quickbook-test list_test ]
     [ quickbook-test cond_phrase ]
+ [ quickbook-test macro ]
     [ quickbook-test doc-info-1 ]
     [ quickbook-test doc-info-2 ]
     [ quickbook-test doc-info-3 ]


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