xref: /aosp_15_r20/prebuilts/build-tools/common/bison/skeletons/variant.hh (revision cda5da8d549138a6648c5ee6d7a49cf8f4a657be)
1*cda5da8dSAndroid Build Coastguard Worker # C++ skeleton for Bison
2*cda5da8dSAndroid Build Coastguard Worker 
3*cda5da8dSAndroid Build Coastguard Worker # Copyright (C) 2002-2015, 2018-2021 Free Software Foundation, Inc.
4*cda5da8dSAndroid Build Coastguard Worker 
5*cda5da8dSAndroid Build Coastguard Worker # This program is free software: you can redistribute it and/or modify
6*cda5da8dSAndroid Build Coastguard Worker # it under the terms of the GNU General Public License as published by
7*cda5da8dSAndroid Build Coastguard Worker # the Free Software Foundation, either version 3 of the License, or
8*cda5da8dSAndroid Build Coastguard Worker # (at your option) any later version.
9*cda5da8dSAndroid Build Coastguard Worker #
10*cda5da8dSAndroid Build Coastguard Worker # This program is distributed in the hope that it will be useful,
11*cda5da8dSAndroid Build Coastguard Worker # but WITHOUT ANY WARRANTY; without even the implied warranty of
12*cda5da8dSAndroid Build Coastguard Worker # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13*cda5da8dSAndroid Build Coastguard Worker # GNU General Public License for more details.
14*cda5da8dSAndroid Build Coastguard Worker #
15*cda5da8dSAndroid Build Coastguard Worker # You should have received a copy of the GNU General Public License
16*cda5da8dSAndroid Build Coastguard Worker # along with this program.  If not, see <https://www.gnu.org/licenses/>.
17*cda5da8dSAndroid Build Coastguard Worker 
18*cda5da8dSAndroid Build Coastguard Worker 
19*cda5da8dSAndroid Build Coastguard Worker ## --------- ##
20*cda5da8dSAndroid Build Coastguard Worker ## variant.  ##
21*cda5da8dSAndroid Build Coastguard Worker ## --------- ##
22*cda5da8dSAndroid Build Coastguard Worker 
23*cda5da8dSAndroid Build Coastguard Worker # b4_assert
24*cda5da8dSAndroid Build Coastguard Worker # ---------
25*cda5da8dSAndroid Build Coastguard Worker # The name of YY_ASSERT.
26*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_assert],
27*cda5da8dSAndroid Build Coastguard Worker           [b4_api_PREFIX[]_ASSERT])
28*cda5da8dSAndroid Build Coastguard Worker 
29*cda5da8dSAndroid Build Coastguard Worker 
30*cda5da8dSAndroid Build Coastguard Worker # b4_symbol_variant(YYTYPE, YYVAL, ACTION, [ARGS])
31*cda5da8dSAndroid Build Coastguard Worker # ------------------------------------------------
32*cda5da8dSAndroid Build Coastguard Worker # Run some ACTION ("build", or "destroy") on YYVAL of symbol type
33*cda5da8dSAndroid Build Coastguard Worker # YYTYPE.
34*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_symbol_variant],
35*cda5da8dSAndroid Build Coastguard Worker [m4_pushdef([b4_dollar_dollar],
36*cda5da8dSAndroid Build Coastguard Worker             [$2.$3< $][3 > (m4_shift3($@))])dnl
37*cda5da8dSAndroid Build Coastguard Worker switch ($1)
38*cda5da8dSAndroid Build Coastguard Worker     {
39*cda5da8dSAndroid Build Coastguard Worker b4_type_foreach([_b4_type_action])[]dnl
40*cda5da8dSAndroid Build Coastguard Worker       default:
41*cda5da8dSAndroid Build Coastguard Worker         break;
42*cda5da8dSAndroid Build Coastguard Worker     }
43*cda5da8dSAndroid Build Coastguard Worker m4_popdef([b4_dollar_dollar])dnl
44*cda5da8dSAndroid Build Coastguard Worker ])
45*cda5da8dSAndroid Build Coastguard Worker 
46*cda5da8dSAndroid Build Coastguard Worker 
47*cda5da8dSAndroid Build Coastguard Worker # _b4_char_sizeof_counter
48*cda5da8dSAndroid Build Coastguard Worker # -----------------------
49*cda5da8dSAndroid Build Coastguard Worker # A counter used by _b4_char_sizeof_dummy to create fresh symbols.
50*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_char_sizeof_counter],
51*cda5da8dSAndroid Build Coastguard Worker [0])
52*cda5da8dSAndroid Build Coastguard Worker 
53*cda5da8dSAndroid Build Coastguard Worker # _b4_char_sizeof_dummy
54*cda5da8dSAndroid Build Coastguard Worker # ---------------------
55*cda5da8dSAndroid Build Coastguard Worker # At each call return a new C++ identifier.
56*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_char_sizeof_dummy],
57*cda5da8dSAndroid Build Coastguard Worker [m4_define([_b4_char_sizeof_counter], m4_incr(_b4_char_sizeof_counter))dnl
58*cda5da8dSAndroid Build Coastguard Worker dummy[]_b4_char_sizeof_counter])
59*cda5da8dSAndroid Build Coastguard Worker 
60*cda5da8dSAndroid Build Coastguard Worker 
61*cda5da8dSAndroid Build Coastguard Worker # b4_char_sizeof(SYMBOL-NUMS)
62*cda5da8dSAndroid Build Coastguard Worker # ---------------------------
63*cda5da8dSAndroid Build Coastguard Worker # To be mapped on the list of type names to produce:
64*cda5da8dSAndroid Build Coastguard Worker #
65*cda5da8dSAndroid Build Coastguard Worker #    char dummy1[sizeof (type_name_1)];
66*cda5da8dSAndroid Build Coastguard Worker #    char dummy2[sizeof (type_name_2)];
67*cda5da8dSAndroid Build Coastguard Worker #
68*cda5da8dSAndroid Build Coastguard Worker # for defined type names.
69*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_char_sizeof],
70*cda5da8dSAndroid Build Coastguard Worker [b4_symbol_if([$1], [has_type],
71*cda5da8dSAndroid Build Coastguard Worker [
72*cda5da8dSAndroid Build Coastguard Worker m4_map([      b4_symbol_tag_comment], [$@])dnl
73*cda5da8dSAndroid Build Coastguard Worker       char _b4_char_sizeof_dummy@{sizeof (b4_symbol([$1], [type]))@};
74*cda5da8dSAndroid Build Coastguard Worker ])])
75*cda5da8dSAndroid Build Coastguard Worker 
76*cda5da8dSAndroid Build Coastguard Worker 
77*cda5da8dSAndroid Build Coastguard Worker # b4_variant_includes
78*cda5da8dSAndroid Build Coastguard Worker # -------------------
79*cda5da8dSAndroid Build Coastguard Worker # The needed includes for variants support.
80*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_variant_includes],
81*cda5da8dSAndroid Build Coastguard Worker [b4_parse_assert_if([[#include <typeinfo>
82*cda5da8dSAndroid Build Coastguard Worker #ifndef ]b4_assert[
83*cda5da8dSAndroid Build Coastguard Worker # include <cassert>
84*cda5da8dSAndroid Build Coastguard Worker # define ]b4_assert[ assert
85*cda5da8dSAndroid Build Coastguard Worker #endif
86*cda5da8dSAndroid Build Coastguard Worker ]])])
87*cda5da8dSAndroid Build Coastguard Worker 
88*cda5da8dSAndroid Build Coastguard Worker 
89*cda5da8dSAndroid Build Coastguard Worker 
90*cda5da8dSAndroid Build Coastguard Worker ## -------------------------- ##
91*cda5da8dSAndroid Build Coastguard Worker ## Adjustments for variants.  ##
92*cda5da8dSAndroid Build Coastguard Worker ## -------------------------- ##
93*cda5da8dSAndroid Build Coastguard Worker 
94*cda5da8dSAndroid Build Coastguard Worker 
95*cda5da8dSAndroid Build Coastguard Worker # b4_value_type_declare
96*cda5da8dSAndroid Build Coastguard Worker # ---------------------
97*cda5da8dSAndroid Build Coastguard Worker # Define value_type.
98*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_value_type_declare],
99*cda5da8dSAndroid Build Coastguard Worker [[  /// A buffer to store and retrieve objects.
100*cda5da8dSAndroid Build Coastguard Worker   ///
101*cda5da8dSAndroid Build Coastguard Worker   /// Sort of a variant, but does not keep track of the nature
102*cda5da8dSAndroid Build Coastguard Worker   /// of the stored data, since that knowledge is available
103*cda5da8dSAndroid Build Coastguard Worker   /// via the current parser state.
104*cda5da8dSAndroid Build Coastguard Worker   class value_type
105*cda5da8dSAndroid Build Coastguard Worker   {
106*cda5da8dSAndroid Build Coastguard Worker   public:
107*cda5da8dSAndroid Build Coastguard Worker     /// Type of *this.
108*cda5da8dSAndroid Build Coastguard Worker     typedef value_type self_type;
109*cda5da8dSAndroid Build Coastguard Worker 
110*cda5da8dSAndroid Build Coastguard Worker     /// Empty construction.
111*cda5da8dSAndroid Build Coastguard Worker     value_type () YY_NOEXCEPT
112*cda5da8dSAndroid Build Coastguard Worker       : yyraw_ ()]b4_parse_assert_if([
113*cda5da8dSAndroid Build Coastguard Worker       , yytypeid_ (YY_NULLPTR)])[
114*cda5da8dSAndroid Build Coastguard Worker     {}
115*cda5da8dSAndroid Build Coastguard Worker 
116*cda5da8dSAndroid Build Coastguard Worker     /// Construct and fill.
117*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
118*cda5da8dSAndroid Build Coastguard Worker     value_type (YY_RVREF (T) t)]b4_parse_assert_if([
119*cda5da8dSAndroid Build Coastguard Worker       : yytypeid_ (&typeid (T))])[
120*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([[
121*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (sizeof (T) <= size);]])[
122*cda5da8dSAndroid Build Coastguard Worker       new (yyas_<T> ()) T (YY_MOVE (t));
123*cda5da8dSAndroid Build Coastguard Worker     }
124*cda5da8dSAndroid Build Coastguard Worker 
125*cda5da8dSAndroid Build Coastguard Worker #if 201103L <= YY_CPLUSPLUS
126*cda5da8dSAndroid Build Coastguard Worker     /// Non copyable.
127*cda5da8dSAndroid Build Coastguard Worker     value_type (const self_type&) = delete;
128*cda5da8dSAndroid Build Coastguard Worker     /// Non copyable.
129*cda5da8dSAndroid Build Coastguard Worker     self_type& operator= (const self_type&) = delete;
130*cda5da8dSAndroid Build Coastguard Worker #endif
131*cda5da8dSAndroid Build Coastguard Worker 
132*cda5da8dSAndroid Build Coastguard Worker     /// Destruction, allowed only if empty.
133*cda5da8dSAndroid Build Coastguard Worker     ~value_type () YY_NOEXCEPT
134*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([
135*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (!yytypeid_);
136*cda5da8dSAndroid Build Coastguard Worker     ])[}
137*cda5da8dSAndroid Build Coastguard Worker 
138*cda5da8dSAndroid Build Coastguard Worker # if 201103L <= YY_CPLUSPLUS
139*cda5da8dSAndroid Build Coastguard Worker     /// Instantiate a \a T in here from \a t.
140*cda5da8dSAndroid Build Coastguard Worker     template <typename T, typename... U>
141*cda5da8dSAndroid Build Coastguard Worker     T&
142*cda5da8dSAndroid Build Coastguard Worker     emplace (U&&... u)
143*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([[
144*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (!yytypeid_);
145*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (sizeof (T) <= size);
146*cda5da8dSAndroid Build Coastguard Worker       yytypeid_ = & typeid (T);]])[
147*cda5da8dSAndroid Build Coastguard Worker       return *new (yyas_<T> ()) T (std::forward <U>(u)...);
148*cda5da8dSAndroid Build Coastguard Worker     }
149*cda5da8dSAndroid Build Coastguard Worker # else
150*cda5da8dSAndroid Build Coastguard Worker     /// Instantiate an empty \a T in here.
151*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
152*cda5da8dSAndroid Build Coastguard Worker     T&
153*cda5da8dSAndroid Build Coastguard Worker     emplace ()
154*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([[
155*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (!yytypeid_);
156*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (sizeof (T) <= size);
157*cda5da8dSAndroid Build Coastguard Worker       yytypeid_ = & typeid (T);]])[
158*cda5da8dSAndroid Build Coastguard Worker       return *new (yyas_<T> ()) T ();
159*cda5da8dSAndroid Build Coastguard Worker     }
160*cda5da8dSAndroid Build Coastguard Worker 
161*cda5da8dSAndroid Build Coastguard Worker     /// Instantiate a \a T in here from \a t.
162*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
163*cda5da8dSAndroid Build Coastguard Worker     T&
164*cda5da8dSAndroid Build Coastguard Worker     emplace (const T& t)
165*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([[
166*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (!yytypeid_);
167*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (sizeof (T) <= size);
168*cda5da8dSAndroid Build Coastguard Worker       yytypeid_ = & typeid (T);]])[
169*cda5da8dSAndroid Build Coastguard Worker       return *new (yyas_<T> ()) T (t);
170*cda5da8dSAndroid Build Coastguard Worker     }
171*cda5da8dSAndroid Build Coastguard Worker # endif
172*cda5da8dSAndroid Build Coastguard Worker 
173*cda5da8dSAndroid Build Coastguard Worker     /// Instantiate an empty \a T in here.
174*cda5da8dSAndroid Build Coastguard Worker     /// Obsolete, use emplace.
175*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
176*cda5da8dSAndroid Build Coastguard Worker     T&
177*cda5da8dSAndroid Build Coastguard Worker     build ()
178*cda5da8dSAndroid Build Coastguard Worker     {
179*cda5da8dSAndroid Build Coastguard Worker       return emplace<T> ();
180*cda5da8dSAndroid Build Coastguard Worker     }
181*cda5da8dSAndroid Build Coastguard Worker 
182*cda5da8dSAndroid Build Coastguard Worker     /// Instantiate a \a T in here from \a t.
183*cda5da8dSAndroid Build Coastguard Worker     /// Obsolete, use emplace.
184*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
185*cda5da8dSAndroid Build Coastguard Worker     T&
186*cda5da8dSAndroid Build Coastguard Worker     build (const T& t)
187*cda5da8dSAndroid Build Coastguard Worker     {
188*cda5da8dSAndroid Build Coastguard Worker       return emplace<T> (t);
189*cda5da8dSAndroid Build Coastguard Worker     }
190*cda5da8dSAndroid Build Coastguard Worker 
191*cda5da8dSAndroid Build Coastguard Worker     /// Accessor to a built \a T.
192*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
193*cda5da8dSAndroid Build Coastguard Worker     T&
194*cda5da8dSAndroid Build Coastguard Worker     as () YY_NOEXCEPT
195*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([[
196*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (yytypeid_);
197*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (*yytypeid_ == typeid (T));
198*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (sizeof (T) <= size);]])[
199*cda5da8dSAndroid Build Coastguard Worker       return *yyas_<T> ();
200*cda5da8dSAndroid Build Coastguard Worker     }
201*cda5da8dSAndroid Build Coastguard Worker 
202*cda5da8dSAndroid Build Coastguard Worker     /// Const accessor to a built \a T (for %printer).
203*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
204*cda5da8dSAndroid Build Coastguard Worker     const T&
205*cda5da8dSAndroid Build Coastguard Worker     as () const YY_NOEXCEPT
206*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([[
207*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (yytypeid_);
208*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (*yytypeid_ == typeid (T));
209*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (sizeof (T) <= size);]])[
210*cda5da8dSAndroid Build Coastguard Worker       return *yyas_<T> ();
211*cda5da8dSAndroid Build Coastguard Worker     }
212*cda5da8dSAndroid Build Coastguard Worker 
213*cda5da8dSAndroid Build Coastguard Worker     /// Swap the content with \a that, of same type.
214*cda5da8dSAndroid Build Coastguard Worker     ///
215*cda5da8dSAndroid Build Coastguard Worker     /// Both variants must be built beforehand, because swapping the actual
216*cda5da8dSAndroid Build Coastguard Worker     /// data requires reading it (with as()), and this is not possible on
217*cda5da8dSAndroid Build Coastguard Worker     /// unconstructed variants: it would require some dynamic testing, which
218*cda5da8dSAndroid Build Coastguard Worker     /// should not be the variant's responsibility.
219*cda5da8dSAndroid Build Coastguard Worker     /// Swapping between built and (possibly) non-built is done with
220*cda5da8dSAndroid Build Coastguard Worker     /// self_type::move ().
221*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
222*cda5da8dSAndroid Build Coastguard Worker     void
223*cda5da8dSAndroid Build Coastguard Worker     swap (self_type& that) YY_NOEXCEPT
224*cda5da8dSAndroid Build Coastguard Worker     {]b4_parse_assert_if([[
225*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (yytypeid_);
226*cda5da8dSAndroid Build Coastguard Worker       ]b4_assert[ (*yytypeid_ == *that.yytypeid_);]])[
227*cda5da8dSAndroid Build Coastguard Worker       std::swap (as<T> (), that.as<T> ());
228*cda5da8dSAndroid Build Coastguard Worker     }
229*cda5da8dSAndroid Build Coastguard Worker 
230*cda5da8dSAndroid Build Coastguard Worker     /// Move the content of \a that to this.
231*cda5da8dSAndroid Build Coastguard Worker     ///
232*cda5da8dSAndroid Build Coastguard Worker     /// Destroys \a that.
233*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
234*cda5da8dSAndroid Build Coastguard Worker     void
235*cda5da8dSAndroid Build Coastguard Worker     move (self_type& that)
236*cda5da8dSAndroid Build Coastguard Worker     {
237*cda5da8dSAndroid Build Coastguard Worker # if 201103L <= YY_CPLUSPLUS
238*cda5da8dSAndroid Build Coastguard Worker       emplace<T> (std::move (that.as<T> ()));
239*cda5da8dSAndroid Build Coastguard Worker # else
240*cda5da8dSAndroid Build Coastguard Worker       emplace<T> ();
241*cda5da8dSAndroid Build Coastguard Worker       swap<T> (that);
242*cda5da8dSAndroid Build Coastguard Worker # endif
243*cda5da8dSAndroid Build Coastguard Worker       that.destroy<T> ();
244*cda5da8dSAndroid Build Coastguard Worker     }
245*cda5da8dSAndroid Build Coastguard Worker 
246*cda5da8dSAndroid Build Coastguard Worker # if 201103L <= YY_CPLUSPLUS
247*cda5da8dSAndroid Build Coastguard Worker     /// Move the content of \a that to this.
248*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
249*cda5da8dSAndroid Build Coastguard Worker     void
250*cda5da8dSAndroid Build Coastguard Worker     move (self_type&& that)
251*cda5da8dSAndroid Build Coastguard Worker     {
252*cda5da8dSAndroid Build Coastguard Worker       emplace<T> (std::move (that.as<T> ()));
253*cda5da8dSAndroid Build Coastguard Worker       that.destroy<T> ();
254*cda5da8dSAndroid Build Coastguard Worker     }
255*cda5da8dSAndroid Build Coastguard Worker #endif
256*cda5da8dSAndroid Build Coastguard Worker 
257*cda5da8dSAndroid Build Coastguard Worker     /// Copy the content of \a that to this.
258*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
259*cda5da8dSAndroid Build Coastguard Worker     void
260*cda5da8dSAndroid Build Coastguard Worker     copy (const self_type& that)
261*cda5da8dSAndroid Build Coastguard Worker     {
262*cda5da8dSAndroid Build Coastguard Worker       emplace<T> (that.as<T> ());
263*cda5da8dSAndroid Build Coastguard Worker     }
264*cda5da8dSAndroid Build Coastguard Worker 
265*cda5da8dSAndroid Build Coastguard Worker     /// Destroy the stored \a T.
266*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
267*cda5da8dSAndroid Build Coastguard Worker     void
268*cda5da8dSAndroid Build Coastguard Worker     destroy ()
269*cda5da8dSAndroid Build Coastguard Worker     {
270*cda5da8dSAndroid Build Coastguard Worker       as<T> ().~T ();]b4_parse_assert_if([
271*cda5da8dSAndroid Build Coastguard Worker       yytypeid_ = YY_NULLPTR;])[
272*cda5da8dSAndroid Build Coastguard Worker     }
273*cda5da8dSAndroid Build Coastguard Worker 
274*cda5da8dSAndroid Build Coastguard Worker   private:
275*cda5da8dSAndroid Build Coastguard Worker #if YY_CPLUSPLUS < 201103L
276*cda5da8dSAndroid Build Coastguard Worker     /// Non copyable.
277*cda5da8dSAndroid Build Coastguard Worker     value_type (const self_type&);
278*cda5da8dSAndroid Build Coastguard Worker     /// Non copyable.
279*cda5da8dSAndroid Build Coastguard Worker     self_type& operator= (const self_type&);
280*cda5da8dSAndroid Build Coastguard Worker #endif
281*cda5da8dSAndroid Build Coastguard Worker 
282*cda5da8dSAndroid Build Coastguard Worker     /// Accessor to raw memory as \a T.
283*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
284*cda5da8dSAndroid Build Coastguard Worker     T*
285*cda5da8dSAndroid Build Coastguard Worker     yyas_ () YY_NOEXCEPT
286*cda5da8dSAndroid Build Coastguard Worker     {
287*cda5da8dSAndroid Build Coastguard Worker       void *yyp = yyraw_;
288*cda5da8dSAndroid Build Coastguard Worker       return static_cast<T*> (yyp);
289*cda5da8dSAndroid Build Coastguard Worker      }
290*cda5da8dSAndroid Build Coastguard Worker 
291*cda5da8dSAndroid Build Coastguard Worker     /// Const accessor to raw memory as \a T.
292*cda5da8dSAndroid Build Coastguard Worker     template <typename T>
293*cda5da8dSAndroid Build Coastguard Worker     const T*
294*cda5da8dSAndroid Build Coastguard Worker     yyas_ () const YY_NOEXCEPT
295*cda5da8dSAndroid Build Coastguard Worker     {
296*cda5da8dSAndroid Build Coastguard Worker       const void *yyp = yyraw_;
297*cda5da8dSAndroid Build Coastguard Worker       return static_cast<const T*> (yyp);
298*cda5da8dSAndroid Build Coastguard Worker      }
299*cda5da8dSAndroid Build Coastguard Worker 
300*cda5da8dSAndroid Build Coastguard Worker     /// An auxiliary type to compute the largest semantic type.
301*cda5da8dSAndroid Build Coastguard Worker     union union_type
302*cda5da8dSAndroid Build Coastguard Worker     {]b4_type_foreach([b4_char_sizeof])[    };
303*cda5da8dSAndroid Build Coastguard Worker 
304*cda5da8dSAndroid Build Coastguard Worker     /// The size of the largest semantic type.
305*cda5da8dSAndroid Build Coastguard Worker     enum { size = sizeof (union_type) };
306*cda5da8dSAndroid Build Coastguard Worker 
307*cda5da8dSAndroid Build Coastguard Worker     /// A buffer to store semantic values.
308*cda5da8dSAndroid Build Coastguard Worker     union
309*cda5da8dSAndroid Build Coastguard Worker     {
310*cda5da8dSAndroid Build Coastguard Worker       /// Strongest alignment constraints.
311*cda5da8dSAndroid Build Coastguard Worker       long double yyalign_me_;
312*cda5da8dSAndroid Build Coastguard Worker       /// A buffer large enough to store any of the semantic values.
313*cda5da8dSAndroid Build Coastguard Worker       char yyraw_[size];
314*cda5da8dSAndroid Build Coastguard Worker     };]b4_parse_assert_if([
315*cda5da8dSAndroid Build Coastguard Worker 
316*cda5da8dSAndroid Build Coastguard Worker     /// Whether the content is built: if defined, the name of the stored type.
317*cda5da8dSAndroid Build Coastguard Worker     const std::type_info *yytypeid_;])[
318*cda5da8dSAndroid Build Coastguard Worker   };
319*cda5da8dSAndroid Build Coastguard Worker ]])
320*cda5da8dSAndroid Build Coastguard Worker 
321*cda5da8dSAndroid Build Coastguard Worker 
322*cda5da8dSAndroid Build Coastguard Worker # How the semantic value is extracted when using variants.
323*cda5da8dSAndroid Build Coastguard Worker 
324*cda5da8dSAndroid Build Coastguard Worker # b4_symbol_value(VAL, SYMBOL-NUM, [TYPE])
325*cda5da8dSAndroid Build Coastguard Worker # ----------------------------------------
326*cda5da8dSAndroid Build Coastguard Worker # See README.
327*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_symbol_value],
328*cda5da8dSAndroid Build Coastguard Worker [m4_ifval([$3],
329*cda5da8dSAndroid Build Coastguard Worker           [$1.as< $3 > ()],
330*cda5da8dSAndroid Build Coastguard Worker           [m4_ifval([$2],
331*cda5da8dSAndroid Build Coastguard Worker                     [b4_symbol_if([$2], [has_type],
332*cda5da8dSAndroid Build Coastguard Worker                                   [$1.as < b4_symbol([$2], [type]) > ()],
333*cda5da8dSAndroid Build Coastguard Worker                                   [$1])],
334*cda5da8dSAndroid Build Coastguard Worker                     [$1])])])
335*cda5da8dSAndroid Build Coastguard Worker 
336*cda5da8dSAndroid Build Coastguard Worker # b4_symbol_value_template(VAL, SYMBOL-NUM, [TYPE])
337*cda5da8dSAndroid Build Coastguard Worker # -------------------------------------------------
338*cda5da8dSAndroid Build Coastguard Worker # Same as b4_symbol_value, but used in a template method.
339*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_symbol_value_template],
340*cda5da8dSAndroid Build Coastguard Worker [m4_ifval([$3],
341*cda5da8dSAndroid Build Coastguard Worker           [$1.template as< $3 > ()],
342*cda5da8dSAndroid Build Coastguard Worker           [m4_ifval([$2],
343*cda5da8dSAndroid Build Coastguard Worker                     [b4_symbol_if([$2], [has_type],
344*cda5da8dSAndroid Build Coastguard Worker                                   [$1.template as < b4_symbol([$2], [type]) > ()],
345*cda5da8dSAndroid Build Coastguard Worker                                   [$1])],
346*cda5da8dSAndroid Build Coastguard Worker                     [$1])])])
347*cda5da8dSAndroid Build Coastguard Worker 
348*cda5da8dSAndroid Build Coastguard Worker 
349*cda5da8dSAndroid Build Coastguard Worker 
350*cda5da8dSAndroid Build Coastguard Worker ## ------------- ##
351*cda5da8dSAndroid Build Coastguard Worker ## make_SYMBOL.  ##
352*cda5da8dSAndroid Build Coastguard Worker ## ------------- ##
353*cda5da8dSAndroid Build Coastguard Worker 
354*cda5da8dSAndroid Build Coastguard Worker 
355*cda5da8dSAndroid Build Coastguard Worker # _b4_includes_tokens(SYMBOL-NUM...)
356*cda5da8dSAndroid Build Coastguard Worker # ----------------------------------
357*cda5da8dSAndroid Build Coastguard Worker # Expands to non-empty iff one of the SYMBOL-NUM denotes
358*cda5da8dSAndroid Build Coastguard Worker # a token.
359*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_is_token],
360*cda5da8dSAndroid Build Coastguard Worker           [b4_symbol_if([$1], [is_token], [1])])
361*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_includes_tokens],
362*cda5da8dSAndroid Build Coastguard Worker           [m4_map([_b4_is_token], [$@])])
363*cda5da8dSAndroid Build Coastguard Worker 
364*cda5da8dSAndroid Build Coastguard Worker 
365*cda5da8dSAndroid Build Coastguard Worker # _b4_token_maker_define(SYMBOL-NUM)
366*cda5da8dSAndroid Build Coastguard Worker # ----------------------------------
367*cda5da8dSAndroid Build Coastguard Worker # Declare make_SYMBOL for SYMBOL-NUM.  Use at class-level.
368*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_token_maker_define],
369*cda5da8dSAndroid Build Coastguard Worker [b4_token_visible_if([$1],
370*cda5da8dSAndroid Build Coastguard Worker [#if 201103L <= YY_CPLUSPLUS
371*cda5da8dSAndroid Build Coastguard Worker       static
372*cda5da8dSAndroid Build Coastguard Worker       symbol_type
373*cda5da8dSAndroid Build Coastguard Worker       make_[]_b4_symbol([$1], [id]) (b4_join(
374*cda5da8dSAndroid Build Coastguard Worker                  b4_symbol_if([$1], [has_type],
375*cda5da8dSAndroid Build Coastguard Worker                  [b4_symbol([$1], [type]) v]),
376*cda5da8dSAndroid Build Coastguard Worker                  b4_locations_if([location_type l])))
377*cda5da8dSAndroid Build Coastguard Worker       {
378*cda5da8dSAndroid Build Coastguard Worker         return symbol_type (b4_join([token::b4_symbol([$1], [id])],
379*cda5da8dSAndroid Build Coastguard Worker                                     b4_symbol_if([$1], [has_type], [std::move (v)]),
380*cda5da8dSAndroid Build Coastguard Worker                                     b4_locations_if([std::move (l)])));
381*cda5da8dSAndroid Build Coastguard Worker       }
382*cda5da8dSAndroid Build Coastguard Worker #else
383*cda5da8dSAndroid Build Coastguard Worker       static
384*cda5da8dSAndroid Build Coastguard Worker       symbol_type
385*cda5da8dSAndroid Build Coastguard Worker       make_[]_b4_symbol([$1], [id]) (b4_join(
386*cda5da8dSAndroid Build Coastguard Worker                  b4_symbol_if([$1], [has_type],
387*cda5da8dSAndroid Build Coastguard Worker                  [const b4_symbol([$1], [type])& v]),
388*cda5da8dSAndroid Build Coastguard Worker                  b4_locations_if([const location_type& l])))
389*cda5da8dSAndroid Build Coastguard Worker       {
390*cda5da8dSAndroid Build Coastguard Worker         return symbol_type (b4_join([token::b4_symbol([$1], [id])],
391*cda5da8dSAndroid Build Coastguard Worker                                     b4_symbol_if([$1], [has_type], [v]),
392*cda5da8dSAndroid Build Coastguard Worker                                     b4_locations_if([l])));
393*cda5da8dSAndroid Build Coastguard Worker       }
394*cda5da8dSAndroid Build Coastguard Worker #endif
395*cda5da8dSAndroid Build Coastguard Worker ])])
396*cda5da8dSAndroid Build Coastguard Worker 
397*cda5da8dSAndroid Build Coastguard Worker 
398*cda5da8dSAndroid Build Coastguard Worker # b4_token_kind(SYMBOL-NUM)
399*cda5da8dSAndroid Build Coastguard Worker # -------------------------
400*cda5da8dSAndroid Build Coastguard Worker # Some tokens don't have an ID.
401*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_token_kind],
402*cda5da8dSAndroid Build Coastguard Worker [b4_symbol_if([$1], [has_id],
403*cda5da8dSAndroid Build Coastguard Worker               [token::b4_symbol([$1], [id])],
404*cda5da8dSAndroid Build Coastguard Worker               [b4_symbol([$1], [code])])])
405*cda5da8dSAndroid Build Coastguard Worker 
406*cda5da8dSAndroid Build Coastguard Worker 
407*cda5da8dSAndroid Build Coastguard Worker # _b4_tok_in(SYMBOL-NUM, ...)
408*cda5da8dSAndroid Build Coastguard Worker # ---------------------------
409*cda5da8dSAndroid Build Coastguard Worker # See b4_tok_in below.  The SYMBOL-NUMs... are tokens only.
410*cda5da8dSAndroid Build Coastguard Worker #
411*cda5da8dSAndroid Build Coastguard Worker # We iterate over the tokens to group them by "range" of token numbers (not
412*cda5da8dSAndroid Build Coastguard Worker # symbols numbers!).
413*cda5da8dSAndroid Build Coastguard Worker #
414*cda5da8dSAndroid Build Coastguard Worker # b4_fst is the start of that range.
415*cda5da8dSAndroid Build Coastguard Worker # b4_prev is the previous value.
416*cda5da8dSAndroid Build Coastguard Worker # b4_val is the current value.
417*cda5da8dSAndroid Build Coastguard Worker # If b4_val is the successor of b4_prev in token numbers, update the latter,
418*cda5da8dSAndroid Build Coastguard Worker #   otherwise emit the code for range b4_fst .. b4_prev.
419*cda5da8dSAndroid Build Coastguard Worker # $1 is also used as a terminator in the foreach, but it will not be printed.
420*cda5da8dSAndroid Build Coastguard Worker #
421*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_tok_in],
422*cda5da8dSAndroid Build Coastguard Worker [m4_pushdef([b4_prev], [$1])dnl
423*cda5da8dSAndroid Build Coastguard Worker m4_pushdef([b4_fst], [$1])dnl
424*cda5da8dSAndroid Build Coastguard Worker m4_pushdef([b4_sep], [])dnl
425*cda5da8dSAndroid Build Coastguard Worker m4_foreach([b4_val], m4_dquote(m4_shift($@, $1)),
426*cda5da8dSAndroid Build Coastguard Worker            [m4_if(b4_symbol(b4_val, [code]), m4_eval(b4_symbol(b4_prev, [code]) + 1), [],
427*cda5da8dSAndroid Build Coastguard Worker                   [b4_sep[]m4_if(b4_fst, b4_prev,
428*cda5da8dSAndroid Build Coastguard Worker                          [tok == b4_token_kind(b4_fst)],
429*cda5da8dSAndroid Build Coastguard Worker                          [(b4_token_kind(b4_fst) <= tok && tok <= b4_token_kind(b4_prev))])[]dnl
430*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_fst], b4_val)dnl
431*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_sep], [
432*cda5da8dSAndroid Build Coastguard Worker                    || ])])dnl
433*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_prev], b4_val)])dnl
434*cda5da8dSAndroid Build Coastguard Worker m4_popdef([b4_sep])dnl
435*cda5da8dSAndroid Build Coastguard Worker m4_popdef([b4_fst])dnl
436*cda5da8dSAndroid Build Coastguard Worker m4_popdef([b4_prev])dnl
437*cda5da8dSAndroid Build Coastguard Worker ])
438*cda5da8dSAndroid Build Coastguard Worker 
439*cda5da8dSAndroid Build Coastguard Worker 
440*cda5da8dSAndroid Build Coastguard Worker # _b4_filter_tokens(SYMBOL-NUM, ...)
441*cda5da8dSAndroid Build Coastguard Worker # ----------------------------------
442*cda5da8dSAndroid Build Coastguard Worker # Expand as the list of tokens amongst SYMBOL-NUM.
443*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_filter_tokens],
444*cda5da8dSAndroid Build Coastguard Worker [m4_pushdef([b4_sep])dnl
445*cda5da8dSAndroid Build Coastguard Worker m4_foreach([b4_val], [$@],
446*cda5da8dSAndroid Build Coastguard Worker            [b4_symbol_if(b4_val, [is_token], [b4_sep[]b4_val[]m4_define([b4_sep], [,])])])dnl
447*cda5da8dSAndroid Build Coastguard Worker m4_popdef([b4_sep])dnl
448*cda5da8dSAndroid Build Coastguard Worker ])
449*cda5da8dSAndroid Build Coastguard Worker 
450*cda5da8dSAndroid Build Coastguard Worker 
451*cda5da8dSAndroid Build Coastguard Worker # b4_tok_in(SYMBOL-NUM, ...)
452*cda5da8dSAndroid Build Coastguard Worker # ---------------------------
453*cda5da8dSAndroid Build Coastguard Worker # A C++ conditional that checks that `tok` is a member of this list of symbol
454*cda5da8dSAndroid Build Coastguard Worker # numbers.
455*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_tok_in],
456*cda5da8dSAndroid Build Coastguard Worker           [_$0(_b4_filter_tokens($@))])
457*cda5da8dSAndroid Build Coastguard Worker 
458*cda5da8dSAndroid Build Coastguard Worker 
459*cda5da8dSAndroid Build Coastguard Worker 
460*cda5da8dSAndroid Build Coastguard Worker 
461*cda5da8dSAndroid Build Coastguard Worker # _b4_symbol_constructor_define(SYMBOL-NUM...)
462*cda5da8dSAndroid Build Coastguard Worker # --------------------------------------------
463*cda5da8dSAndroid Build Coastguard Worker # Define a symbol_type constructor common to all the SYMBOL-NUM (they
464*cda5da8dSAndroid Build Coastguard Worker # have the same type).  Use at class-level.
465*cda5da8dSAndroid Build Coastguard Worker m4_define([_b4_symbol_constructor_define],
466*cda5da8dSAndroid Build Coastguard Worker [m4_ifval(_b4_includes_tokens($@),
467*cda5da8dSAndroid Build Coastguard Worker [[#if 201103L <= YY_CPLUSPLUS
468*cda5da8dSAndroid Build Coastguard Worker       symbol_type (]b4_join(
469*cda5da8dSAndroid Build Coastguard Worker           [int tok],
470*cda5da8dSAndroid Build Coastguard Worker           b4_symbol_if([$1], [has_type],
471*cda5da8dSAndroid Build Coastguard Worker                        [b4_symbol([$1], [type]) v]),
472*cda5da8dSAndroid Build Coastguard Worker           b4_locations_if([location_type l]))[)
473*cda5da8dSAndroid Build Coastguard Worker         : super_type (]b4_join([token_kind_type (tok)],
474*cda5da8dSAndroid Build Coastguard Worker                                b4_symbol_if([$1], [has_type], [std::move (v)]),
475*cda5da8dSAndroid Build Coastguard Worker                                b4_locations_if([std::move (l)]))[)
476*cda5da8dSAndroid Build Coastguard Worker #else
477*cda5da8dSAndroid Build Coastguard Worker       symbol_type (]b4_join(
478*cda5da8dSAndroid Build Coastguard Worker           [int tok],
479*cda5da8dSAndroid Build Coastguard Worker           b4_symbol_if([$1], [has_type],
480*cda5da8dSAndroid Build Coastguard Worker                        [const b4_symbol([$1], [type])& v]),
481*cda5da8dSAndroid Build Coastguard Worker           b4_locations_if([const location_type& l]))[)
482*cda5da8dSAndroid Build Coastguard Worker         : super_type (]b4_join([token_kind_type (tok)],
483*cda5da8dSAndroid Build Coastguard Worker                                b4_symbol_if([$1], [has_type], [v]),
484*cda5da8dSAndroid Build Coastguard Worker                                b4_locations_if([l]))[)
485*cda5da8dSAndroid Build Coastguard Worker #endif
486*cda5da8dSAndroid Build Coastguard Worker       {]b4_parse_assert_if([[
487*cda5da8dSAndroid Build Coastguard Worker #if !defined _MSC_VER || defined __clang__
488*cda5da8dSAndroid Build Coastguard Worker         ]b4_assert[ (]b4_tok_in($@)[);
489*cda5da8dSAndroid Build Coastguard Worker #endif
490*cda5da8dSAndroid Build Coastguard Worker       ]])[}
491*cda5da8dSAndroid Build Coastguard Worker ]])])
492*cda5da8dSAndroid Build Coastguard Worker 
493*cda5da8dSAndroid Build Coastguard Worker 
494*cda5da8dSAndroid Build Coastguard Worker # b4_basic_symbol_constructor_define(SYMBOL-NUM)
495*cda5da8dSAndroid Build Coastguard Worker # ----------------------------------------------
496*cda5da8dSAndroid Build Coastguard Worker # Generate a constructor for basic_symbol from given type.
497*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_basic_symbol_constructor_define],
498*cda5da8dSAndroid Build Coastguard Worker [[#if 201103L <= YY_CPLUSPLUS
499*cda5da8dSAndroid Build Coastguard Worker       basic_symbol (]b4_join(
500*cda5da8dSAndroid Build Coastguard Worker           [typename Base::kind_type t],
501*cda5da8dSAndroid Build Coastguard Worker           b4_symbol_if([$1], [has_type], [b4_symbol([$1], [type])&& v]),
502*cda5da8dSAndroid Build Coastguard Worker           b4_locations_if([location_type&& l]))[)
503*cda5da8dSAndroid Build Coastguard Worker         : Base (t)]b4_symbol_if([$1], [has_type], [
504*cda5da8dSAndroid Build Coastguard Worker         , value (std::move (v))])[]b4_locations_if([
505*cda5da8dSAndroid Build Coastguard Worker         , location (std::move (l))])[
506*cda5da8dSAndroid Build Coastguard Worker       {}
507*cda5da8dSAndroid Build Coastguard Worker #else
508*cda5da8dSAndroid Build Coastguard Worker       basic_symbol (]b4_join(
509*cda5da8dSAndroid Build Coastguard Worker           [typename Base::kind_type t],
510*cda5da8dSAndroid Build Coastguard Worker           b4_symbol_if([$1], [has_type], [const b4_symbol([$1], [type])& v]),
511*cda5da8dSAndroid Build Coastguard Worker           b4_locations_if([const location_type& l]))[)
512*cda5da8dSAndroid Build Coastguard Worker         : Base (t)]b4_symbol_if([$1], [has_type], [
513*cda5da8dSAndroid Build Coastguard Worker         , value (v)])[]b4_locations_if([
514*cda5da8dSAndroid Build Coastguard Worker         , location (l)])[
515*cda5da8dSAndroid Build Coastguard Worker       {}
516*cda5da8dSAndroid Build Coastguard Worker #endif
517*cda5da8dSAndroid Build Coastguard Worker ]])
518*cda5da8dSAndroid Build Coastguard Worker 
519*cda5da8dSAndroid Build Coastguard Worker 
520*cda5da8dSAndroid Build Coastguard Worker # b4_token_constructor_define
521*cda5da8dSAndroid Build Coastguard Worker # ---------------------------
522*cda5da8dSAndroid Build Coastguard Worker # Define the overloaded versions of make_FOO for all the token kinds.
523*cda5da8dSAndroid Build Coastguard Worker m4_define([b4_token_constructor_define],
524*cda5da8dSAndroid Build Coastguard Worker [    // Implementation of make_symbol for each token kind.
525*cda5da8dSAndroid Build Coastguard Worker b4_symbol_foreach([_b4_token_maker_define])])
526