This replaces the recursion and implicit call stack usage of the DFS
executor with iteration and an explicit heap-based stack.  After this
patch, we no longer stack overflow on the PR86164 testcases since stack
usage is minimal.  Besides reduced stack usage, this should be a
non-functional change.  Readability rather than optimal heap usage is
emphasized.  There's some low-hanging fruit for optimizing heap usage
that I'll submit as follow-up patches.

Since the signature of _Executor was changed by the previous patch via
the __dfs_mode template parameter removal, and _Executor is an internal
type that users can't name, I believe there's no ABI issues or risks of
mixing old/new version member functions?

        PR libstdc++/86164

libstdc++-v3/ChangeLog:

        * include/bits/regex_executor.h (__detail::_ExecutorFrame):
        Declare.
        (__detail::_ExecutorFrameVec): Declare.
        (__detail::_Executor::_ExecutorFrame): Declare.
        (__detail::_Executor::_ExecutorFrameVec): Declare.
        (__detail::_Executor): Add _ExecutorFrameVec& parameter to each
        subroutine of _M_dfs.
        (__detail::_Executor::_M_node): Declare.
        (__detail::_Executor::_M_dfs): Remove __start parameter.
        * include/bits/regex_executor.tcc (__detail::_ExecutorFrameOpcode):
        New.
        (__detail::_ExecutorFrame): New.
        (__detail::_Executor::_M_main_dispatch): Adjust _M_dfs call
        after _StateId parameter removal.
        (__detail::_Executor::_M_rep_once_more): Add _ExecutorFrame&
        parameter.  Replace recursive _M_dfs calls with a _S_opcode_next
        frame push, and any tail work after such calls with an
        appropriate frame push.
        (__detail::_M_handle_repeat): Likewise.
        (__detail::_M_handle_subexpr_begin): Likewise.
        (__detail::_M_handle_subexpr_end): Likewise.
        (__detail::_M_handle_line_begin_assertion): Likewise.
        (__detail::_M_handle_line_end_assertion): Likewise.
        (__detail::_M_handle_word_boundary): Likewise.
        (__detail::_M_handle_subexpr_lookahead): Likewise.
        (__detail::_M_handle_match): Likewise.
        (__detail::_M_handle_backref): Likewise.
        (__detail::_M_handle_accept): Likewise.
        (__detail::_M_handle_alternative): Likewise.
        (__detail::_M_node): Factored out from _M_dfs.
        (__detail::_M_dfs): Remove _StateIdT parameter.  Create an
        _ExecutorFrameVec stack with an initial frame that visits the
        starting node and pass this stack each subroutine.  Pop the
        latest _ExecutorFrame from the stack and handle appropriately
        according to its _ExecutorFrameOpcode.  Loop until the stack
        is empty.
---
 libstdc++-v3/include/bits/regex_executor.h   |  38 ++-
 libstdc++-v3/include/bits/regex_executor.tcc | 281 ++++++++++++++-----
 2 files changed, 230 insertions(+), 89 deletions(-)

diff --git a/libstdc++-v3/include/bits/regex_executor.h 
b/libstdc++-v3/include/bits/regex_executor.h
index 0c3f7f9050b0..a51018fd0134 100644
--- a/libstdc++-v3/include/bits/regex_executor.h
+++ b/libstdc++-v3/include/bits/regex_executor.h
@@ -41,6 +41,12 @@ namespace __detail
    * @{
    */
 
+  template<typename _BiIter, bool _Trivial = 
is_trivially_copyable<_BiIter>::value>
+    struct _ExecutorFrame;
+
+  template<typename _BiIter>
+    using _ExecutorFrameVec = _GLIBCXX_STD_C::vector<_ExecutorFrame<_BiIter>>;
+
   /**
    * @brief Takes a regex and an input string and does the matching.
    */
@@ -98,44 +104,50 @@ namespace __detail
       _M_search();
 
     private:
+      using _ExecutorFrame = __detail::_ExecutorFrame<_BiIter>;
+      using _ExecutorFrameVec = __detail::_ExecutorFrameVec<_BiIter>;
+
+      void
+      _M_rep_once_more(_Match_mode, _StateIdT, _ExecutorFrameVec&);
+
       void
-      _M_rep_once_more(_Match_mode __match_mode, _StateIdT);
+      _M_handle_repeat(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_repeat(_Match_mode, _StateIdT);
+      _M_handle_subexpr_begin(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_subexpr_begin(_Match_mode, _StateIdT);
+      _M_handle_subexpr_end(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_subexpr_end(_Match_mode, _StateIdT);
+      _M_handle_line_begin_assertion(_Match_mode, _StateIdT, 
_ExecutorFrameVec&);
 
       void
-      _M_handle_line_begin_assertion(_Match_mode, _StateIdT);
+      _M_handle_line_end_assertion(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_line_end_assertion(_Match_mode, _StateIdT);
+      _M_handle_word_boundary(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_word_boundary(_Match_mode, _StateIdT);
+      _M_handle_subexpr_lookahead(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_subexpr_lookahead(_Match_mode, _StateIdT);
+      _M_handle_match(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_match(_Match_mode, _StateIdT);
+      _M_handle_backref(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_backref(_Match_mode, _StateIdT);
+      _M_handle_accept(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_accept(_Match_mode, _StateIdT);
+      _M_handle_alternative(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_handle_alternative(_Match_mode, _StateIdT);
+      _M_node(_Match_mode, _StateIdT, _ExecutorFrameVec&);
 
       void
-      _M_dfs(_Match_mode __match_mode, _StateIdT __start);
+      _M_dfs(_Match_mode);
 
       bool
       _M_main(_Match_mode __match_mode)
diff --git a/libstdc++-v3/include/bits/regex_executor.tcc 
b/libstdc++-v3/include/bits/regex_executor.tcc
index 58d5a2bfec3a..0e78cb2e2c87 100644
--- a/libstdc++-v3/include/bits/regex_executor.tcc
+++ b/libstdc++-v3/include/bits/regex_executor.tcc
@@ -54,15 +54,72 @@ namespace __detail
       return false;
     }
 
-  // The _M_main function operates in different modes, DFS mode or BFS mode,
-  // indicated by template parameter __dfs_mode, and dispatches to one of the
-  // _M_main_dispatch overloads.
-  //
-  // ------------------------------------------------------------
-  //
-  // DFS mode:
-  //
-  // It applies a Depth-First-Search (aka backtracking) on given NFA and input
+  enum _ExecutorFrameOpcode : unsigned char
+  {
+    _S_fopcode_next,
+    _S_fopcode_fallback_next,
+    _S_fopcode_rep_once_more,
+    _S_fopcode_fallback_rep_once_more,
+    _S_fopcode_posix_alternative,
+    _S_fopcode_merge_sol,
+    _S_fopcode_restore_current,
+    _S_fopcode_restore_subexpr_begin,
+    _S_fopcode_restore_subexpr_end,
+    _S_fopcode_restore_rep_count_pos,
+    _S_fopcode_restore_rep_count_val,
+    _S_fopcode_decrement_rep_count,
+  };
+
+  template<typename _BiIter, bool _Trivial /* = 
is_trivially_copyable<_BiIter>::value */>
+    struct _ExecutorFrame
+    {
+      _ExecutorFrame(_ExecutorFrameOpcode __op, _StateIdT __i)
+      : _M_op(__op), _M_state_id(__i)
+      { }
+
+      _ExecutorFrame(_ExecutorFrameOpcode __op, _StateIdT __i, _BiIter __p)
+      : _M_op(__op), _M_state_id(__i), _M_pos(__p)
+      { }
+
+      _ExecutorFrame(_ExecutorFrameOpcode __op, _StateIdT __i, long __v)
+      : _M_op(__op), _M_state_id(__i), _M_val(__v)
+      { }
+
+      _ExecutorFrameOpcode _M_op;
+      _StateIdT _M_state_id;
+      // _M_pos and _M_val are mutually exclusive, which is more obvious
+      // in the optimized partial specialization below.
+      _BiIter _M_pos = _BiIter();
+      long _M_val = 0;
+    };
+
+  // Space-optimized partial specialization for when the input iterator is
+  // trivially copyable.
+  template<typename _BiIter>
+    struct _ExecutorFrame<_BiIter, true>
+    {
+      _ExecutorFrame(_ExecutorFrameOpcode __op, _StateIdT __i)
+      : _M_op(__op), _M_state_id(__i)
+      { }
+
+      _ExecutorFrame(_ExecutorFrameOpcode __op, _StateIdT __i, _BiIter __p)
+      : _M_op(__op), _M_state_id(__i), _M_pos(__p)
+      { }
+
+      _ExecutorFrame(_ExecutorFrameOpcode __op, _StateIdT __i, long __v)
+      : _M_op(__op), _M_state_id(__i), _M_val(__v)
+      { }
+
+      _ExecutorFrameOpcode _M_op;
+      _StateIdT _M_state_id;
+      union
+      {
+       _BiIter _M_pos;
+       long _M_val;
+      };
+    };
+
+  // Apply a Depth-First-Search (aka backtracking) on given NFA and input
   // string.
   // At the very beginning the executor stands in the start state, then it
   // tries every possible state transition in current state recursively. Some
@@ -84,7 +141,7 @@ namespace __detail
       _M_has_sol = false;
       *_M_states._M_get_sol_pos() = _BiIter();
       _M_cur_results = _M_results;
-      _M_dfs(__match_mode, _M_states._M_start);
+      _M_dfs(__match_mode);
       return _M_has_sol;
     }
 
@@ -117,25 +174,28 @@ namespace __detail
   // we need to spare one more time for potential group capture.
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_rep_once_more(_Match_mode __match_mode, _StateIdT __i)
+    _M_rep_once_more(_Match_mode, _StateIdT __i,
+                    _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
       auto& __rep_count = _M_rep_count[__i];
       if (__rep_count.second == 0 || __rep_count.first != _M_current)
        {
-         auto __back = __rep_count;
+         __frames.emplace_back(_S_fopcode_restore_rep_count_val,
+                               __i, __rep_count.second);
+         __frames.emplace_back(_S_fopcode_restore_rep_count_pos,
+                               __i, __rep_count.first);
          __rep_count.first = _M_current;
          __rep_count.second = 1;
-         _M_dfs(__match_mode, __state._M_alt);
-         __rep_count = __back;
+         __frames.emplace_back(_S_fopcode_next, __state._M_alt);
        }
       else
        {
          if (__rep_count.second < 2)
            {
              __rep_count.second++;
-             _M_dfs(__match_mode, __state._M_alt);
-             __rep_count.second--;
+             __frames.emplace_back(_S_fopcode_decrement_rep_count, __i);
+             __frames.emplace_back(_S_fopcode_next, __state._M_alt);
            }
        }
     }
@@ -146,105 +206,105 @@ namespace __detail
   // given greedy mode.
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_repeat(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_repeat(_Match_mode, _StateIdT __i,
+                    _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
-
       // Greedy.
       if (!__state._M_neg)
        {
-         _M_rep_once_more(__match_mode, __i);
-         // If we already accepted, we're done.
-         if (!_M_has_sol)
-           _M_dfs(__match_mode, __state._M_next);
+         __frames.emplace_back(_S_fopcode_fallback_next, __state._M_next);
+         __frames.emplace_back(_S_fopcode_rep_once_more, __i);
        }
       else // Non-greedy mode
        {
-         // vice-versa.
-         _M_dfs(__match_mode, __state._M_next);
-         if (!_M_has_sol)
-           _M_rep_once_more(__match_mode, __i);
+         __frames.emplace_back(_S_fopcode_fallback_rep_once_more, __i);
+         __frames.emplace_back(_S_fopcode_next, __state._M_next);
        }
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_subexpr_begin(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_subexpr_begin(_Match_mode, _StateIdT __i,
+                           _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
-
       auto& __res = _M_cur_results[__state._M_subexpr];
-      auto __back = __res.first;
+      __frames.emplace_back(_S_fopcode_restore_subexpr_begin,
+                           __state._M_subexpr, __res.first);
       __res.first = _M_current;
-      _M_dfs(__match_mode, __state._M_next);
-      __res.first = __back;
+      __frames.emplace_back(_S_fopcode_next, __state._M_next);
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_subexpr_end(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_subexpr_end(_Match_mode, _StateIdT __i,
+                         _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
-
       auto& __res = _M_cur_results[__state._M_subexpr];
-      auto __back = __res;
+      __frames.emplace_back(_S_fopcode_restore_subexpr_end,
+                           __state._M_subexpr, __res.second);
       __res.second = _M_current;
       __res.matched = true;
-      _M_dfs(__match_mode, __state._M_next);
-      __res = __back;
+      __frames.emplace_back(_S_fopcode_next, __state._M_next);
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     inline void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_line_begin_assertion(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_line_begin_assertion(_Match_mode, _StateIdT __i,
+                                  _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
       if (_M_at_begin())
-       _M_dfs(__match_mode, __state._M_next);
+       __frames.emplace_back(_S_fopcode_next, __state._M_next);
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     inline void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_line_end_assertion(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_line_end_assertion(_Match_mode, _StateIdT __i,
+                                _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
       if (_M_at_end())
-       _M_dfs(__match_mode, __state._M_next);
+       __frames.emplace_back(_S_fopcode_next, __state._M_next);
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     inline void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_word_boundary(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_word_boundary(_Match_mode, _StateIdT __i,
+                           _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
       if (_M_word_boundary() == !__state._M_neg)
-       _M_dfs(__match_mode, __state._M_next);
+       __frames.emplace_back(_S_fopcode_next, __state._M_next);
     }
 
   // Here __state._M_alt offers a single start node for a sub-NFA.
   // We recursively invoke our algorithm to match the sub-NFA.
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_subexpr_lookahead(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_subexpr_lookahead(_Match_mode, _StateIdT __i,
+                               _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
       if (_M_lookahead(__state._M_alt) == !__state._M_neg)
-       _M_dfs(__match_mode, __state._M_next);
+       __frames.emplace_back(_S_fopcode_next, __state._M_next);
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_match(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_match(_Match_mode, _StateIdT __i,
+                   _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
-
       if (_M_current == _M_end)
        return;
       if (__state._M_matches(*_M_current))
        {
+         __frames.emplace_back(_S_fopcode_restore_current, 0, _M_current);
          ++_M_current;
-         _M_dfs(__match_mode, __state._M_next);
-         --_M_current;
+         __frames.emplace_back(_S_fopcode_next, __state._M_next);
        }
     }
 
@@ -302,7 +362,8 @@ namespace __detail
   // If matched, keep going; else just return and try another state.
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_backref(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_backref(_Match_mode, _StateIdT __i,
+                     _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
       auto& __submatch = _M_cur_results[__state._M_backref_index];
@@ -320,19 +381,19 @@ namespace __detail
        {
          if (__last != _M_current)
            {
-             auto __backup = _M_current;
+             __frames.emplace_back(_S_fopcode_restore_current, 0, _M_current);
              _M_current = __last;
-             _M_dfs(__match_mode, __state._M_next);
-             _M_current = __backup;
+             __frames.emplace_back(_S_fopcode_next, __state._M_next);
            }
          else
-           _M_dfs(__match_mode, __state._M_next);
+           __frames.emplace_back(_S_fopcode_next, __state._M_next);
        }
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_accept(_Match_mode __match_mode, _StateIdT)
+    _M_handle_accept(_Match_mode __match_mode, _StateIdT,
+                    _ExecutorFrameVec&)
     {
       __glibcxx_assert(!_M_has_sol);
       if (__match_mode == _Match_mode::_Exact)
@@ -370,63 +431,131 @@ namespace __detail
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_handle_alternative(_Match_mode __match_mode, _StateIdT __i)
+    _M_handle_alternative(_Match_mode, _StateIdT __i,
+                         _ExecutorFrameVec& __frames)
     {
       const auto& __state = _M_nfa[__i];
-
       if (_M_nfa._M_flags & regex_constants::ECMAScript)
        {
-         _M_dfs(__match_mode, __state._M_alt);
          // Pick lhs if it matches. Only try rhs if it doesn't.
-         if (!_M_has_sol)
-           _M_dfs(__match_mode, __state._M_next);
+         __frames.emplace_back(_S_fopcode_fallback_next, __state._M_next);
+         __frames.emplace_back(_S_fopcode_next, __state._M_alt);
        }
       else
        {
          // Try both and compare the result.
          // See "case _S_opcode_accept:" handling above.
-         _M_dfs(__match_mode, __state._M_alt);
-         auto __has_sol = _M_has_sol;
-         _M_has_sol = false;
-         _M_dfs(__match_mode, __state._M_next);
-         _M_has_sol |= __has_sol;
+         __frames.emplace_back(_S_fopcode_posix_alternative, __state._M_next);
+         __frames.emplace_back(_S_fopcode_next, __state._M_alt);
        }
     }
 
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     void _Executor<_BiIter, _Alloc, _TraitsT>::
-    _M_dfs(_Match_mode __match_mode, _StateIdT __i)
+    _M_node(_Match_mode __match_mode, _StateIdT __i,
+           _ExecutorFrameVec& __frames)
     {
       switch (_M_nfa[__i]._M_opcode())
        {
        case _S_opcode_repeat:
-         _M_handle_repeat(__match_mode, __i); break;
+         _M_handle_repeat(__match_mode, __i, __frames); break;
        case _S_opcode_subexpr_begin:
-         _M_handle_subexpr_begin(__match_mode, __i); break;
+         _M_handle_subexpr_begin(__match_mode, __i, __frames); break;
        case _S_opcode_subexpr_end:
-         _M_handle_subexpr_end(__match_mode, __i); break;
+         _M_handle_subexpr_end(__match_mode, __i, __frames); break;
        case _S_opcode_line_begin_assertion:
-         _M_handle_line_begin_assertion(__match_mode, __i); break;
+         _M_handle_line_begin_assertion(__match_mode, __i, __frames); break;
        case _S_opcode_line_end_assertion:
-         _M_handle_line_end_assertion(__match_mode, __i); break;
+         _M_handle_line_end_assertion(__match_mode, __i, __frames); break;
        case _S_opcode_word_boundary:
-         _M_handle_word_boundary(__match_mode, __i); break;
+         _M_handle_word_boundary(__match_mode, __i, __frames); break;
        case _S_opcode_subexpr_lookahead:
-         _M_handle_subexpr_lookahead(__match_mode, __i); break;
+         _M_handle_subexpr_lookahead(__match_mode, __i, __frames); break;
        case _S_opcode_match:
-         _M_handle_match(__match_mode, __i); break;
+         _M_handle_match(__match_mode, __i, __frames); break;
        case _S_opcode_backref:
-         _M_handle_backref(__match_mode, __i);
+         _M_handle_backref(__match_mode, __i, __frames);
          break;
        case _S_opcode_accept:
-         _M_handle_accept(__match_mode, __i); break;
+         _M_handle_accept(__match_mode, __i, __frames); break;
        case _S_opcode_alternative:
-         _M_handle_alternative(__match_mode, __i); break;
+         _M_handle_alternative(__match_mode, __i, __frames); break;
        default:
          __glibcxx_assert(false);
        }
     }
 
+  template<typename _BiIter, typename _Alloc, typename _TraitsT>
+    void _Executor<_BiIter, _Alloc, _TraitsT>::
+    _M_dfs(_Match_mode __match_mode)
+    {
+      _ExecutorFrameVec __frames;
+      __frames.emplace_back(_S_fopcode_next, _M_states._M_start);
+
+      while (!__frames.empty())
+       {
+         _ExecutorFrame __frame = std::move(__frames.back());
+         __frames.pop_back();
+
+         switch (__frame._M_op)
+           {
+           case _S_fopcode_next:
+             _M_node(__match_mode, __frame._M_state_id, __frames);
+             break;
+
+           case _S_fopcode_fallback_next:
+             if (!_M_has_sol)
+               __frames.emplace_back(_S_fopcode_next, __frame._M_state_id);
+             break;
+
+           case _S_fopcode_fallback_rep_once_more:
+             if (!_M_has_sol)
+               __frames.emplace_back(_S_fopcode_rep_once_more,
+                                     __frame._M_state_id);
+             break;
+
+           case _S_fopcode_rep_once_more:
+             _M_rep_once_more(__match_mode, __frame._M_state_id, __frames);
+             break;
+
+           case _S_fopcode_posix_alternative:
+             __frames.emplace_back(_S_fopcode_merge_sol, 0, _M_has_sol);
+             __frames.emplace_back(_S_fopcode_next, __frame._M_state_id);
+             _M_has_sol = false;
+             break;
+
+           case _S_fopcode_merge_sol:
+             _M_has_sol |= __frame._M_val;
+             break;
+
+           case _S_fopcode_restore_current:
+             _M_current = __frame._M_pos;
+             break;
+
+           case _S_fopcode_restore_subexpr_begin:
+             _M_cur_results[__frame._M_state_id].first = __frame._M_pos;
+             break;
+
+           case _S_fopcode_restore_subexpr_end:
+             _M_cur_results[__frame._M_state_id].second = __frame._M_pos;
+             _M_cur_results[__frame._M_state_id].matched = true;
+             break;
+
+           case _S_fopcode_restore_rep_count_pos:
+             _M_rep_count[__frame._M_state_id].first = __frame._M_pos;
+             break;
+
+           case _S_fopcode_restore_rep_count_val:
+             _M_rep_count[__frame._M_state_id].second = __frame._M_val;
+             break;
+
+           case _S_fopcode_decrement_rep_count:
+             _M_rep_count[__frame._M_state_id].second--;
+             break;
+           }
+       }
+    }
+
   // Return whether now is at some word boundary.
   template<typename _BiIter, typename _Alloc, typename _TraitsT>
     bool _Executor<_BiIter, _Alloc, _TraitsT>::
-- 
2.53.0.rc0.25.gb5c409c40f

Reply via email to