]> git.saurik.com Git - bison.git/blob - data/lalr1.cc
214adb27aca07381a4bd1f85c968ae325812b2e5
[bison.git] / data / lalr1.cc
1 m4_divert(-1)
2 # C++ skeleton for Bison
3 # Copyright (C) 2002, 2003 Free Software Foundation, Inc.
4
5 # This program is free software; you can redistribute it and/or modify
6 # it under the terms of the GNU General Public License as published by
7 # the Free Software Foundation; either version 2 of the License, or
8 # (at your option) any later version.
9
10 # This program is distributed in the hope that it will be useful,
11 # but WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 # GNU General Public License for more details.
14
15 # You should have received a copy of the GNU General Public License
16 # along with this program; if not, write to the Free Software
17 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
18 # 02111-1307 USA
19
20 ## ---------------- ##
21 ## Default values. ##
22 ## ---------------- ##
23
24 # Default Parser class name.
25 m4_define_default([b4_parser_class_name], [Parser])
26
27
28
29 ## ----------------- ##
30 ## Semantic Values. ##
31 ## ----------------- ##
32
33
34 # b4_lhs_value([TYPE])
35 # --------------------
36 # Expansion of $<TYPE>$.
37 m4_define([b4_lhs_value],
38 [yyval[]m4_ifval([$1], [.$1])])
39
40
41 # b4_rhs_value(RULE-LENGTH, NUM, [TYPE])
42 # --------------------------------------
43 # Expansion of $<TYPE>NUM, where the current rule has RULE-LENGTH
44 # symbols on RHS.
45 m4_define([b4_rhs_value],
46 [semantic_stack_@{m4_eval([$1 - $2])@}m4_ifval([$3], [.$3])])
47
48 m4_define_default([b4_location_type], [Location])
49
50 # b4_lhs_location()
51 # -----------------
52 # Expansion of @$.
53 m4_define([b4_lhs_location],
54 [yyloc])
55
56
57 # b4_rhs_location(RULE-LENGTH, NUM)
58 # ---------------------------------
59 # Expansion of @NUM, where the current rule has RULE-LENGTH symbols
60 # on RHS.
61 m4_define([b4_rhs_location],
62 [location_stack_@{m4_eval([$1 - $2])@}])
63
64
65 m4_define([b4_inherit],
66 [m4_ifdef([b4_root],
67 [: public b4_root
68 ],
69 [])])
70
71 m4_define([b4_param],
72 [m4_ifdef([b4_root],
73 [,
74 const Param& param],
75 [])])
76
77 m4_define([b4_constructor],
78 [m4_ifdef([b4_root],
79 [b4_root (param),
80 ],
81 [])])
82
83
84 # We do want M4 expansion after # for CPP macros.
85 m4_changecom()
86 m4_divert(0)dnl
87 m4_if(b4_defines_flag, 0, [],
88 [@output @output_header_name@
89 b4_copyright([C++ Skeleton parser for LALR(1) parsing with Bison],
90 [2002, 2003])[
91 /* FIXME: This is wrong, we want computed header guards.
92 I don't know why the macros are missing now. :( */
93 #ifndef PARSER_HEADER_H
94 # define PARSER_HEADER_H
95
96 #include "stack.hh"
97 #include "location.hh"
98
99 #include <string>
100 #include <iostream>
101
102 /* Using locations. */
103 #define YYLSP_NEEDED ]b4_locations_flag[
104
105 ]b4_token_defines(b4_tokens)[
106
107 /* Copy the first part of user declarations. */
108 ]b4_pre_prologue[
109
110 ]/* Line __line__ of lalr1.cc. */
111 b4_syncline([@oline@], [@ofile@])[
112
113 /* Enabling traces. */
114 #ifndef YYDEBUG
115 # define YYDEBUG ]b4_debug[
116 #endif
117
118 /* Enabling verbose error message. */
119 #ifndef YYERROR_VERBOSE
120 # define YYERROR_VERBOSE ]b4_error_verbose[
121 #endif
122
123 #ifndef YYSTYPE
124 ]m4_ifdef([b4_stype],
125 [b4_syncline([b4_stype_line], [b4_filename])
126 typedef union b4_stype yystype;
127 /* Line __line__ of lalr1.cc. */
128 b4_syncline([@oline@], [@ofile@])],
129 [typedef int yystype;])[
130 # define YYSTYPE yystype
131 #endif
132
133 /* Copy the second part of user declarations. */
134 ]b4_post_prologue[
135
136 ]/* Line __line__ of lalr1.cc. */
137 b4_syncline([@oline@], [@ofile@])[
138 #ifndef YYLLOC_DEFAULT
139 # define YYLLOC_DEFAULT(Current, Rhs, N) \
140 Current.end = Rhs[N].end;
141 #endif
142
143 namespace yy
144 {
145 class ]b4_parser_class_name[;
146
147 template < typename P >
148 struct Traits
149 {
150 };
151
152 template < >
153 struct Traits< ]b4_parser_class_name[ >
154 {
155 typedef ]b4_int_type_for([b4_translate])[ TokenNumberType;
156 typedef ]b4_int_type_for([b4_rhs])[ RhsNumberType;
157 typedef int StateType;
158 typedef yystype SemanticType;
159 typedef ]b4_location_type[ LocationType;
160 };
161 }
162
163 namespace yy
164 {
165 class ]b4_parser_class_name b4_inherit[
166 {
167 public:
168
169 typedef Traits< ]b4_parser_class_name[ >::TokenNumberType TokenNumberType;
170 typedef Traits< ]b4_parser_class_name[ >::RhsNumberType RhsNumberType;
171 typedef Traits< ]b4_parser_class_name[ >::StateType StateType;
172 typedef Traits< ]b4_parser_class_name[ >::SemanticType SemanticType;
173 typedef Traits< ]b4_parser_class_name[ >::LocationType LocationType;
174
175 typedef Stack< StateType > StateStack;
176 typedef Stack< SemanticType > SemanticStack;
177 typedef Stack< LocationType > LocationStack;
178
179 #if YYLSP_NEEDED
180 ]b4_parser_class_name[ (bool debug,
181 LocationType initlocation][]b4_param[) :
182 ]b4_constructor[][debug_ (debug),
183 cdebug_ (std::cerr),
184 initlocation_ (initlocation)
185 #else
186 ]b4_parser_class_name[ (bool debug][]b4_param[) :
187 ]b4_constructor[][debug_ (debug),
188 cdebug_ (std::cerr)
189 #endif
190 {
191 }
192
193 virtual ~]b4_parser_class_name[ ()
194 {
195 }
196
197 virtual int parse ();
198
199 private:
200
201 virtual void lex_ ();
202 virtual void error_ ();
203 virtual void print_ ();
204
205 /* Stacks. */
206 StateStack state_stack_;
207 SemanticStack semantic_stack_;
208 LocationStack location_stack_;
209
210 /* Tables. */
211 static const ]b4_int_type_for([b4_pact])[ pact_[];
212 static const ]b4_int_type_for([b4_pact])[ pact_ninf_;
213 static const ]b4_int_type_for([b4_defact])[ defact_[];
214 static const ]b4_int_type_for([b4_pgoto])[ pgoto_[];
215 static const ]b4_int_type_for([b4_defgoto])[ defgoto_[];
216 static const ]b4_int_type_for([b4_table])[ table_[];
217 static const ]b4_int_type_for([b4_table])[ table_ninf_;
218 static const ]b4_int_type_for([b4_check])[ check_[];
219 static const ]b4_int_type_for([b4_r1])[ r1_[];
220 static const ]b4_int_type_for([b4_r2])[ r2_[];
221
222 #if YYDEBUG || YYERROR_VERBOSE
223 static const char* const name_[];
224 #endif
225
226 /* More tables, for debugging. */
227 #if YYDEBUG
228 static const RhsNumberType rhs_[];
229 static const ]b4_int_type_for([b4_prhs])[ prhs_[];
230 static const ]b4_int_type_for([b4_rline])[ rline_[];
231 static const ]b4_int_type_for([b4_stos])[ stos_[];
232 static const ]b4_int_type_for([b4_toknum])[ token_number_[];
233 #endif
234
235 /* Even more tables. */
236 static inline TokenNumberType translate_ (int token);
237
238 /* Constants. */
239 static const int eof_;
240 /* LAST_ -- Last index in TABLE_. */
241 static const int last_;
242 static const int nnts_;
243 static const int empty_;
244 static const int final_;
245 static const int terror_;
246 static const int errcode_;
247 static const int ntokens_;
248 static const unsigned user_token_number_max_;
249 static const TokenNumberType undef_token_;
250
251 /* State. */
252 int n_;
253 int len_;
254 int state_;
255
256 /* Debugging. */
257 int debug_;
258 std::ostream &cdebug_;
259
260 /* Lookahead and lookahead in internal form. */
261 int looka_;
262 int ilooka_;
263
264 /* Message. */
265 std::string message;
266
267 /* Semantic value and location of lookahead token. */
268 SemanticType value;
269 LocationType location;
270
271 /* @@$ and $$. */
272 SemanticType yyval;
273 LocationType yyloc;
274
275 /* Initial location. */
276 LocationType initlocation_;
277 };
278 }
279
280 #endif /* ! defined PARSER_HEADER_H */]
281 ])dnl
282 @output @output_parser_name@
283 b4_copyright([C++ Skeleton parser for LALR(1) parsing with Bison],
284 [2002, 2003])
285
286 m4_if(b4_defines_flag, 0, [], [#include @output_header_name@])[
287
288 /* Enable debugging if requested. */
289 #if YYDEBUG
290 # define YYCDEBUG if (debug_) cdebug_
291 #else /* !YYDEBUG */
292 # define YYCDEBUG if (0) cdebug_
293 #endif /* !YYDEBUG */
294
295 #define YYACCEPT goto yyacceptlab
296 #define YYABORT goto yyabortlab
297 #define YYERROR goto yyerrlab1
298
299
300 int
301 yy::]b4_parser_class_name[::parse ()
302 {
303 int nerrs = 0;
304 int errstatus = 0;
305
306 /* Initialize the stacks. The initial state will be pushed in
307 yynewstate, since the latter expects the semantical and the
308 location values to have been already stored, initialize these
309 stacks with a primary value. */
310 state_stack_ = StateStack (0);
311 semantic_stack_ = SemanticStack (1);
312 location_stack_ = LocationStack (1);
313
314 /* Start. */
315 state_ = 0;
316 looka_ = empty_;
317 #if YYLSP_NEEDED
318 location = initlocation_;
319 #endif
320 YYCDEBUG << "Starting parse" << std::endl;
321
322 /* New state. */
323 yynewstate:
324 state_stack_.push (state_);
325 YYCDEBUG << "Entering state " << state_ << std::endl;
326 goto yybackup;
327
328 /* Backup. */
329 yybackup:
330
331 /* Try to take a decision without lookahead. */
332 n_ = pact_[state_];
333 if (n_ == pact_ninf_)
334 goto yydefault;
335
336 /* Read a lookahead token. */
337 if (looka_ == empty_)
338 {
339 YYCDEBUG << "Reading a token: ";
340 lex_ ();
341 }
342
343 /* Convert token to internal form. */
344 if (looka_ <= 0)
345 {
346 looka_ = eof_;
347 ilooka_ = 0;
348 YYCDEBUG << "Now at end of input." << std::endl;
349 }
350 else
351 {
352 ilooka_ = translate_ (looka_);
353 #if YYDEBUG
354 if (debug_)
355 {
356 YYCDEBUG << "Next token is " << looka_
357 << " (" << name_[ilooka_];
358 print_ ();
359 YYCDEBUG << ')' << std::endl;
360 }
361 #endif
362 }
363
364 n_ += ilooka_;
365 if (n_ < 0 || last_ < n_ || check_[n_] != ilooka_)
366 goto yydefault;
367
368 /* Reduce or error. */
369 n_ = table_[n_];
370 if (n_ < 0)
371 {
372 if (n_ == table_ninf_)
373 goto yyerrlab;
374 else
375 {
376 n_ = -n_;
377 goto yyreduce;
378 }
379 }
380 else if (n_ == 0)
381 goto yyerrlab;
382
383 /* Accept? */
384 if (n_ == final_)
385 goto yyacceptlab;
386
387 /* Shift the lookahead token. */
388 #if YYDEBUG
389 YYCDEBUG << "Shifting token " << looka_
390 << " (" << name_[ilooka_] << "), ";
391 #endif
392
393 /* Discard the token being shifted unless it is eof. */
394 if (looka_ != eof_)
395 looka_ = empty_;
396
397 semantic_stack_.push (value);
398 location_stack_.push (location);
399
400 /* Count tokens shifted since error; after three, turn off error
401 status. */
402 if (errstatus)
403 --errstatus;
404
405 state_ = n_;
406 goto yynewstate;
407
408 /* Default action. */
409 yydefault:
410 n_ = defact_[state_];
411 if (n_ == 0)
412 goto yyerrlab;
413 goto yyreduce;
414
415 /* Reduce. */
416 yyreduce:
417 len_ = r2_[n_];
418 if (len_)
419 {
420 yyval = semantic_stack_[len_ - 1];
421 yyloc = location_stack_[len_ - 1];
422 }
423 else
424 {
425 yyval = semantic_stack_[0];
426 yyloc = location_stack_[0];
427 }
428
429 #if YYDEBUG
430 if (debug_)
431 {
432 YYCDEBUG << "Reducing via rule " << n_ - 1
433 << " (line " << rline_[n_] << "), ";
434 for (]b4_int_type_for([b4_prhs])[ i = prhs_[n_];
435 0 <= rhs_[i]; ++i)
436 YYCDEBUG << name_[rhs_[i]] << ' ';
437 YYCDEBUG << "-> " << name_[r1_[n_]] << std::endl;
438 }
439 #endif
440
441 if (len_)
442 {
443 Slice< LocationType, LocationStack > slice (location_stack_, len_);
444 YYLLOC_DEFAULT (yyloc, slice, len_);
445 }
446
447 switch (n_)
448 {
449 ]b4_actions[
450 }
451
452 ]/* Line __line__ of lalr1.cc. */
453 b4_syncline([@oline@], [@ofile@])[
454
455 state_stack_.pop (len_);
456 semantic_stack_.pop (len_);
457 location_stack_.pop (len_);
458
459 #if YYDEBUG
460 if (debug_)
461 {
462 YYCDEBUG << "state stack now";
463 for (StateStack::ConstIterator i = state_stack_.begin ();
464 i != state_stack_.end (); ++i)
465 YYCDEBUG << ' ' << *i;
466 YYCDEBUG << std::endl;
467 }
468 #endif
469
470 semantic_stack_.push (yyval);
471 location_stack_.push (yyloc);
472
473 /* Shift the result of the reduction. */
474 n_ = r1_[n_];
475 state_ = pgoto_[n_ - ntokens_] + state_stack_[0];
476 if (0 <= state_ && state_ <= last_ && check_[state_] == state_stack_[0])
477 state_ = table_[state_];
478 else
479 state_ = defgoto_[n_ - ntokens_];
480 goto yynewstate;
481
482 /* Report and recover from errors. This is very incomplete. */
483 yyerrlab:
484 /* If not already recovering from an error, report this error. */
485 if (!errstatus)
486 {
487 ++nerrs;
488
489 #if YYERROR_VERBOSE
490 n_ = pact_[state_];
491 if (pact_ninf_ < n_ && n_ < last_)
492 {
493 message = "syntax error, unexpected ";
494 message += name_[ilooka_];
495 {
496 int count = 0;
497 for (int x = (n_ < 0 ? -n_ : 0); x < ntokens_ + nnts_; ++x)
498 if (check_[x + n_] == x && x != terror_)
499 ++count;
500 if (count < 5)
501 {
502 count = 0;
503 for (int x = (n_ < 0 ? -n_ : 0); x < ntokens_ + nnts_; ++x)
504 if (check_[x + n_] == x && x != terror_)
505 {
506 message += (!count++) ? ", expecting " : " or ";
507 message += name_[x];
508 }
509 }
510 }
511 }
512 else
513 #endif
514 message = "syntax error";
515 error_ ();
516 }
517 goto yyerrlab1;
518
519
520 /*----------------------------------------------------.
521 | yyerrlab1 -- error raised explicitly by an action. |
522 `----------------------------------------------------*/
523 yyerrlab1:
524 if (errstatus == 3)
525 {
526 /* If just tried and failed to reuse lookahead token after an
527 error, discard it. */
528
529 /* Return failure if at end of input. */
530 if (looka_ == eof_)
531 goto yyabortlab;
532 #if YYDEBUG
533 YYCDEBUG << "Discarding token " << looka_
534 << " (" << name_[ilooka_] << ")." << std::endl;
535 #endif
536 looka_ = empty_;
537 }
538
539 /* Else will try to reuse lookahead token after shifting the error
540 token. */
541
542 errstatus = 3;
543
544 for (;;)
545 {
546 n_ = pact_[state_];
547 if (n_ != pact_ninf_)
548 {
549 n_ += terror_;
550 if (0 <= n_ && n_ <= last_ && check_[n_] == terror_)
551 {
552 n_ = table_[n_];
553 if (0 < n_)
554 break;
555 }
556 }
557
558 /* Pop the current state because it cannot handle the error token. */
559 if (state_stack_.height () == 1)
560 goto yyabortlab;
561
562 #if YYDEBUG
563 if (debug_)
564 {
565 if (stos_[state_] < ntokens_)
566 {
567 YYCDEBUG << "Error: popping token "
568 << token_number_[stos_[state_]]
569 << " (" << name_[stos_[state_]];
570 # ifdef YYPRINT
571 YYPRINT (stderr, token_number_[stos_[state_]],
572 semantic_stack_.top ());
573 # endif
574 YYCDEBUG << ')' << std::endl;
575 }
576 else
577 {
578 YYCDEBUG << "Error: popping nonterminal ("
579 << name_[stos_[state_]] << ')' << std::endl;
580 }
581 }
582 #endif
583
584 state_ = (state_stack_.pop (), state_stack_[0]);
585 semantic_stack_.pop ();
586 location_stack_.pop ();;
587
588 #if YYDEBUG
589 if (debug_)
590 {
591 YYCDEBUG << "Error: state stack now";
592 for (StateStack::ConstIterator i = state_stack_.begin ();
593 i != state_stack_.end (); ++i)
594 YYCDEBUG << ' ' << *i;
595 YYCDEBUG << std::endl;
596 }
597 #endif
598 }
599
600 if (n_ == final_)
601 goto yyacceptlab;
602
603 YYCDEBUG << "Shifting error token, ";
604
605 semantic_stack_.push (value);
606 location_stack_.push (location);
607
608 state_ = n_;
609 goto yynewstate;
610
611 /* Accept. */
612 yyacceptlab:
613 return 0;
614
615 /* Abort. */
616 yyabortlab:
617 return 1;
618 }
619
620 void
621 yy::]b4_parser_class_name[::lex_ ()
622 {
623 #if YYLSP_NEEDED
624 looka_ = yylex (&value, &location);
625 #else
626 looka_ = yylex (&value);
627 #endif
628 }
629
630 /* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing
631 STATE-NUM. */
632 const ]b4_int_type_for([b4_pact]) yy::b4_parser_class_name::pact_ninf_ = b4_pact_ninf[;
633 const ]b4_int_type_for([b4_pact])[
634 yy::]b4_parser_class_name[::pact_[] =
635 {
636 ]b4_pact[
637 };
638
639 /* YYDEFACT[S] -- default rule to reduce with in state S when YYTABLE
640 doesn't specify something else to do. Zero means the default is an
641 error. */
642 const ]b4_int_type_for([b4_defact])[
643 yy::]b4_parser_class_name[::defact_[] =
644 {
645 ]b4_defact[
646 };
647
648 /* YYPGOTO[NTERM-NUM]. */
649 const ]b4_int_type_for([b4_pgoto])[
650 yy::]b4_parser_class_name[::pgoto_[] =
651 {
652 ]b4_pgoto[
653 };
654
655 /* YYDEFGOTO[NTERM-NUM]. */
656 const ]b4_int_type_for([b4_defgoto])[
657 yy::]b4_parser_class_name[::defgoto_[] =
658 {
659 ]b4_defgoto[
660 };
661
662 /* YYTABLE[YYPACT[STATE-NUM]]. What to do in state STATE-NUM. If
663 positive, shift that token. If negative, reduce the rule which
664 number is the opposite. If zero, do what YYDEFACT says. */
665 const ]b4_int_type_for([b4_table]) yy::b4_parser_class_name::table_ninf_ = b4_table_ninf[;
666 const ]b4_int_type_for([b4_table])[
667 yy::]b4_parser_class_name[::table_[] =
668 {
669 ]b4_table[
670 };
671
672 /* YYCHECK. */
673 const ]b4_int_type_for([b4_check])[
674 yy::]b4_parser_class_name[::check_[] =
675 {
676 ]b4_check[
677 };
678
679 #if YYDEBUG
680 /* STOS_[STATE-NUM] -- The (internal number of the) accessing
681 symbol of state STATE-NUM. */
682 const ]b4_int_type_for([b4_stos])[
683 yy::]b4_parser_class_name[::stos_[] =
684 {
685 ]b4_stos[
686 };
687
688 /* TOKEN_NUMBER_[YYLEX-NUM] -- Internal token number corresponding
689 to YYLEX-NUM. */
690 const ]b4_int_type_for([b4_toknum])[
691 yy::]b4_parser_class_name[::token_number_[] =
692 {
693 ]b4_toknum[
694 };
695 #endif
696
697 /* YYR1[YYN] -- Symbol number of symbol that rule YYN derives. */
698 const ]b4_int_type_for([b4_r1])[
699 yy::]b4_parser_class_name[::r1_[] =
700 {
701 ]b4_r1[
702 };
703
704 /* YYR2[YYN] -- Number of symbols composing right hand side of rule YYN. */
705 const ]b4_int_type_for([b4_r2])[
706 yy::]b4_parser_class_name[::r2_[] =
707 {
708 ]b4_r2[
709 };
710
711 #if YYDEBUG || YYERROR_VERBOSE
712 /* YYTNAME[SYMBOL-NUM] -- String name of the symbol SYMBOL-NUM.
713 First, the terminals, then, starting at YYNTOKENS, nonterminals. */
714 const char*
715 const yy::]b4_parser_class_name[::name_[] =
716 {
717 ]b4_tname[
718 };
719 #endif
720
721 #if YYDEBUG
722 /* YYRHS -- A `-1'-separated list of the rules' RHS. */
723 const yy::]b4_parser_class_name[::RhsNumberType
724 yy::]b4_parser_class_name[::rhs_[] =
725 {
726 ]b4_rhs[
727 };
728
729 /* YYPRHS[YYN] -- Index of the first RHS symbol of rule number YYN in
730 YYRHS. */
731 const ]b4_int_type_for([b4_prhs])[
732 yy::]b4_parser_class_name[::prhs_[] =
733 {
734 ]b4_prhs[
735 };
736
737 /* YYRLINE[YYN] -- source line where rule number YYN was defined. */
738 const ]b4_int_type_for([b4_rline])[
739 yy::]b4_parser_class_name[::rline_[] =
740 {
741 ]b4_rline[
742 };
743 #endif
744
745 /* YYTRANSLATE(YYLEX) -- Bison symbol number corresponding to YYLEX. */
746 yy::]b4_parser_class_name[::TokenNumberType
747 yy::]b4_parser_class_name[::translate_ (int token)
748 {
749 static
750 const TokenNumberType
751 translate_[] =
752 {
753 ]b4_translate[
754 };
755 if ((unsigned) token <= user_token_number_max_)
756 return translate_[token];
757 else
758 return undef_token_;
759 }
760
761 const int yy::]b4_parser_class_name[::eof_ = 0;
762 const int yy::]b4_parser_class_name[::last_ = ]b4_last[;
763 const int yy::]b4_parser_class_name[::nnts_ = ]b4_nterms_number[;
764 const int yy::]b4_parser_class_name[::empty_ = -2;
765 const int yy::]b4_parser_class_name[::final_ = ]b4_final_state_number[;
766 const int yy::]b4_parser_class_name[::terror_ = 1;
767 const int yy::]b4_parser_class_name[::errcode_ = 256;
768 const int yy::]b4_parser_class_name[::ntokens_ = ]b4_tokens_number[;
769
770 const unsigned yy::]b4_parser_class_name[::user_token_number_max_ = ]b4_user_token_number_max[;
771 const yy::]b4_parser_class_name[::TokenNumberType yy::]b4_parser_class_name[::undef_token_ = ]b4_undef_token_number[;
772
773 ]b4_epilogue
774 dnl
775 @output stack.hh
776 b4_copyright([Stack handling for Bison C++ parsers], [2002, 2003])[
777
778 #ifndef BISON_STACK_HH
779 # define BISON_STACK_HH
780
781 #include <deque>
782
783 namespace yy
784 {
785 template < class T, class S = std::deque< T > >
786 class Stack
787 {
788 public:
789
790 typedef typename S::iterator Iterator;
791 typedef typename S::const_iterator ConstIterator;
792
793 Stack () : seq_ ()
794 {
795 }
796
797 Stack (unsigned n) : seq_ (n)
798 {
799 }
800
801 inline
802 T&
803 operator [] (unsigned index)
804 {
805 return seq_[index];
806 }
807
808 inline
809 const T&
810 operator [] (unsigned index) const
811 {
812 return seq_[index];
813 }
814
815 inline
816 void
817 push (const T& t)
818 {
819 seq_.push_front (t);
820 }
821
822 inline
823 void
824 pop (unsigned n = 1)
825 {
826 for (; n; --n)
827 seq_.pop_front ();
828 }
829
830 inline
831 unsigned
832 height () const
833 {
834 return seq_.size ();
835 }
836
837 inline ConstIterator begin () const { return seq_.begin (); }
838 inline ConstIterator end () const { return seq_.end (); }
839
840 private:
841
842 S seq_;
843 };
844
845 template < class T, class S = Stack< T > >
846 class Slice
847 {
848 public:
849
850 Slice (const S& stack,
851 unsigned range) : stack_ (stack),
852 range_ (range)
853 {
854 }
855
856 inline
857 const T&
858 operator [] (unsigned index) const
859 {
860 return stack_[range_ - index];
861 }
862
863 private:
864
865 const S& stack_;
866 unsigned range_;
867 };
868 }
869
870 #endif // not BISON_STACK_HH]
871 dnl
872 @output location.hh
873 b4_copyright([Location class for Bison C++ parsers], [2002, 2003])[
874
875 #ifndef BISON_LOCATION_HH
876 # define BISON_LOCATION_HH
877
878 # include <iostream>
879 # include <string>
880
881 namespace yy
882 {
883 class Position
884 {
885 public:
886 Position ()
887 : filename (), line (1), column (0)
888 {}
889
890 std::string filename;
891 int line;
892 int column;
893 };
894
895 inline std::ostream&
896 operator<< (std::ostream& ostr, const Position& pos)
897 {
898 if (pos.filename != "")
899 ostr << pos.filename << ':';
900 ostr << pos.line << '.' << pos.column;
901 return ostr;
902 }
903
904 inline Position
905 operator- (const Position& pos, int col)
906 {
907 Position res (pos);
908 res.column -= col;
909 return res;
910 }
911
912
913 class Location
914 {
915 public:
916 Position begin;
917 Position end;
918 };
919
920 /* Don't issue twice the line number when the location is on a single
921 line. */
922
923 inline std::ostream&
924 operator<< (std::ostream& ostr, const Location& pos)
925 {
926 ostr << pos.begin;
927 if (pos.begin.filename != pos.end.filename)
928 ostr << '-' << pos.end - 1;
929 else if (pos.begin.line != pos.end.line)
930 ostr << '-' << pos.end.line << '.' << pos.end.column - 1;
931 else if (pos.begin.column != pos.end.column - 1)
932 ostr << '-' << pos.end.column - 1;
933 return ostr;
934 }
935
936 }
937
938 #endif // not BISON_LOCATION_HH]