From c84134b6440bdae276bd3d1b4d54951ddc75de93 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Fri, 23 Mar 2012 16:05:15 +0100 Subject: [PATCH 01/14] tests: when using the C++ compiler, use its flags too. * tests/local.at: Go for colors. (--compile-c-with-cxx): New option. We used to pass "CC=$CXX" as command line argument, but it was not possible to adjust CFLAGS accordingly in atlocal, since it is loaded before assignments on the command line are honored (so that the command line takes precedence). * tests/atlocal.in: Implement it. * tests/local.mk: Use it. (cherry picked from commit ac3f2e33b464a168b84ddb8a2da2195a6656dd19) Conflicts: tests/local.mk --- tests/Makefile.am | 2 +- tests/atlocal.in | 7 +++++++ tests/local.at | 11 +++++++++++ 3 files changed, 19 insertions(+), 1 deletion(-) diff --git a/tests/Makefile.am b/tests/Makefile.am index bc59d660..7a2139df 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -78,7 +78,7 @@ installcheck-local: # Be real mean with it. .PHONY: maintainer-check-g++ maintainer-check-g++: $(TESTSUITE) - $(TESTSUITE) CC='$(CXX)' + $(TESTSUITE) --compile-c-with-cxx .PHONY: maintainer-check-posix maintainer-check-posix: $(TESTSUITE) diff --git a/tests/atlocal.in b/tests/atlocal.in index 8f5b1a90..11554b33 100644 --- a/tests/atlocal.in +++ b/tests/atlocal.in @@ -62,3 +62,10 @@ CONF_JAVA='@CONF_JAVA@' # Use simple quotes (lib/quote.c). LC_CTYPE=C export LC_CTYPE + + +# Handle --compile-c-with-cxx here, once CXX and CXXFLAGS are known. +if "$at_arg_compile_c_with_cxx"; then + CC=$CXX + CFLAGS=$CXXFLAGS +fi diff --git a/tests/local.at b/tests/local.at index dd4cd555..462301db 100644 --- a/tests/local.at +++ b/tests/local.at @@ -629,4 +629,15 @@ m4_popdef([AT_COND_CASE])]) AT_INIT +# Cannot assign CC and CFLAGS here, since atlocal is loaded after +# options are processed, so we don't know the value of CXX and +# CXXFLAGS yet. +# +# Note that it also means that command line values for CXX and +# CXXFLAGS will not be propagated to CC and CFLAGS. +AT_ARG_OPTION([compile-c-with-cxx], + [compile C parsers with the C++ compiler]) + +AT_COLOR_TESTS + AT_TESTED([bison]) From bbaf618c3e9a5645c5d71bf2ea0de2bdeb8a4976 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Sat, 24 Mar 2012 14:11:06 +0100 Subject: [PATCH 02/14] tests: beware of -pedantic on large #line numbers. * tests/local.at (AT_TEST_TABLES_AND_PARSE): Don't pass -pedantic when compiling large canonical-LR parsers. Reported by Tys Lefering. http://lists.gnu.org/archive/html/bug-bison/2012-03/msg00025.html (cherry picked from commit 8ec3110a9ed4e4d26327bbccfc25278c374fd99a) --- tests/local.at | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/tests/local.at b/tests/local.at index 462301db..d651eb95 100644 --- a/tests/local.at +++ b/tests/local.at @@ -610,6 +610,17 @@ m4_if(m4_index(m4_quote($3), [last-state]), -1, $9 +# Canonical LR generates very large tables, resulting in very long +# files with #line directives that may overflow what the standards +# (C90 and C++98) guarantee: 32767. In that case, GCC's -pedantic +# will issue an error. +# +# There is no "" around `wc` since some indent the result. +m4_bmatch([$4], [%define lr.type canonical-lr], +[if test 32767 -lt `wc -l < input.c`; then + CFLAGS=`echo " $CFLAGS " | sed -e 's/ -pedantic //'` + CXXFLAGS=`echo " $CXXFLAGS " | sed -e 's/ -pedantic //'` +fi]) AT_COMPILE([[input]]) AT_PARSER_CHECK([[./input]], From e34e97bcd736ab3193bfd3abd4162db3b159836d Mon Sep 17 00:00:00 2001 From: Tim Landscheidt Date: Sun, 12 Feb 2012 01:29:41 +0000 Subject: [PATCH 03/14] Java: Fix syntax error handling without error token. * data/lalr1.java (YYParser::parse): Here. * tests/java.at: Add test case. --- data/lalr1.java | 2 +- tests/java.at | 66 +++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 67 insertions(+), 1 deletion(-) diff --git a/data/lalr1.java b/data/lalr1.java index f7f2ba36..b5884c40 100644 --- a/data/lalr1.java +++ b/data/lalr1.java @@ -642,7 +642,7 @@ m4_popdef([b4_at_dollar])])dnl } /* Pop the current state because it cannot handle the error token. */ - if (yystack.height == 1) + if (yystack.height == 0) return false; ]b4_locations_if([yyerrloc = yystack.locationAt (0);])[ diff --git a/tests/java.at b/tests/java.at index e16701df..b9e9deee 100644 --- a/tests/java.at +++ b/tests/java.at @@ -749,3 +749,69 @@ AT_CHECK([[$EGREP -v ' */?\*' YYParser.java | grep 'Position']], [1], [ignore]) AT_CHECK([[$EGREP -v ' */?\*' YYParser.java | grep 'Location']], [1], [ignore]) AT_CLEANUP + + +# ----------------------------------------------- # +# Java syntax error handling without error token. # +# ----------------------------------------------- # + +AT_SETUP([Java syntax error handling without error token]) + +AT_DATA([[YYParser.y]], [[%language "Java" + +%lex-param { String s } + +%code imports { + import java.io.IOException; +} + +%code lexer { + String Input; + int Position; + + public YYLexer (String s) + { + Input = s; + Position = 0; + } + + public void yyerror (String s) + { + System.err.println (s); + } + + public Object getLVal () + { + return null; + } + + public int yylex () throws IOException + { + if (Position >= Input.length ()) + return EOF; + else + return Input.charAt (Position++); + } +} + +%code { + public static void main (String args []) throws IOException + { + YYParser p = new YYParser (args [0]); + p.parse (); + } +} +%% +input: + 'a' 'a' +; +]]) +AT_BISON_CHECK([[YYParser.y]]) +AT_JAVA_COMPILE([[YYParser.java]]) +AT_JAVA_PARSER_CHECK([[YYParser aa]], [[0]], [[]], [[]]) +AT_JAVA_PARSER_CHECK([[YYParser ab]], [[0]], [[]], [[syntax error +]]) +AT_JAVA_PARSER_CHECK([[YYParser ba]], [[0]], [[]], [[syntax error +]]) + +AT_CLEANUP From 041308d0c03783c51ef362f888c957cd2a0e129a Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Tue, 20 Mar 2012 09:27:00 +0100 Subject: [PATCH 04/14] NEWS: update. * NEWS: Java fixes, more about the doc changes, liby issues. --- NEWS | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/NEWS b/NEWS index 28ba8338..838a6868 100644 --- a/NEWS +++ b/NEWS @@ -3,12 +3,29 @@ Bison News * Changes in version 2.5.1 (????-??-??): -** Some portability problems in the test suite have been fixed. +** Several portability problems in the test suite have been fixed: -** Minor improvements have been made to the manual. + This includes warnings with some compilers, unexpected behavior of + tools such as diff, warning messages from the test suite itself, + etc. + +** Warnings during the build procedure have been eliminated. + +** Many minor improvements have been made to the manual: + + The layout for grammar has changed to a more compact scheme. Named + references are motivated. The description of the automaton + description file is updated. ** YYBACKUP works as expected. +** liby is no longer asking for "rpl_fprintf" on some platforms. + +** Several Java fixes: + + The Java parser no longer throws ArrayIndexOutOfBoundsException if + the first token leads to a syntax error. Some minor clean ups. + * Changes in version 2.5 (2011-05-14): ** Grammar symbol names can now contain non-initial dashes: From 37e884cd9a249660f39b5b7290e1f4b3dcc851b0 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Thu, 29 Mar 2012 14:57:25 +0200 Subject: [PATCH 05/14] maint: formatting changes. * src/system.h: Indent CPP directives using cppi. --- src/system.h | 136 +++++++++++++++++++++++++-------------------------- 1 file changed, 68 insertions(+), 68 deletions(-) diff --git a/src/system.h b/src/system.h index 9191b556..e3f17d89 100644 --- a/src/system.h +++ b/src/system.h @@ -16,52 +16,52 @@ along with this program. If not, see . */ #ifndef BISON_SYSTEM_H -#define BISON_SYSTEM_H +# define BISON_SYSTEM_H /* flex 2.5.31 gratutiously defines macros like INT8_MIN. But this runs afoul of pre-C99 compilers that have or , which are included below if available. It also runs afoul of pre-C99 compilers that define these macros in . */ -#if ! defined __STDC_VERSION__ || __STDC_VERSION__ < 199901 -# undef INT8_MIN -# undef INT16_MIN -# undef INT32_MIN -# undef INT8_MAX -# undef INT16_MAX -# undef UINT8_MAX -# undef INT32_MAX -# undef UINT16_MAX -# undef UINT32_MAX -#endif +# if ! defined __STDC_VERSION__ || __STDC_VERSION__ < 199901 +# undef INT8_MIN +# undef INT16_MIN +# undef INT32_MIN +# undef INT8_MAX +# undef INT16_MAX +# undef UINT8_MAX +# undef INT32_MAX +# undef UINT16_MAX +# undef UINT32_MAX +# endif -#include -#include -#include -#include +# include +# include +# include +# include -#if HAVE_SYS_TYPES_H -# include -#endif +# if HAVE_SYS_TYPES_H +# include +# endif -#include -#include +# include +# include -#ifndef UINTPTR_MAX +# ifndef UINTPTR_MAX /* This isn't perfect, but it's good enough for Bison, which needs only to hash pointers. */ typedef size_t uintptr_t; -#endif +# endif // Version mismatch. -#define EX_MISMATCH 63 +# define EX_MISMATCH 63 /*---------. | Gnulib. | `---------*/ -#include -#include -#include +# include +# include +# include /*-----------------. @@ -80,49 +80,49 @@ typedef size_t uintptr_t; and safer logic than it would for users. Due to the overhead of M4, suppressing Code is unlikely to offer any significant improvement in Bison's performance anyway. */ -#define PACIFY_CC(Code) Code +# define PACIFY_CC(Code) Code -#ifndef __attribute__ +# ifndef __attribute__ /* This feature is available in gcc versions 2.5 and later. */ -# if (! defined __GNUC__ || __GNUC__ < 2 \ +# if (! defined __GNUC__ || __GNUC__ < 2 \ || (__GNUC__ == 2 && __GNUC_MINOR__ < 5) || __STRICT_ANSI__) -# define __attribute__(Spec) /* empty */ +# define __attribute__(Spec) /* empty */ +# endif # endif -#endif /* The __-protected variants of `format' and `printf' attributes are accepted by gcc versions 2.6.4 (effectively 2.7) and later. */ -#if __GNUC__ < 2 || (__GNUC__ == 2 && __GNUC_MINOR__ < 7) -# define __format__ format -# define __printf__ printf -#endif +# if __GNUC__ < 2 || (__GNUC__ == 2 && __GNUC_MINOR__ < 7) +# define __format__ format +# define __printf__ printf +# endif -#ifndef ATTRIBUTE_NORETURN -# define ATTRIBUTE_NORETURN __attribute__ ((__noreturn__)) -#endif +# ifndef ATTRIBUTE_NORETURN +# define ATTRIBUTE_NORETURN __attribute__ ((__noreturn__)) +# endif -#ifndef ATTRIBUTE_UNUSED -# define ATTRIBUTE_UNUSED __attribute__ ((__unused__)) -#endif +# ifndef ATTRIBUTE_UNUSED +# define ATTRIBUTE_UNUSED __attribute__ ((__unused__)) +# endif -#define FUNCTION_PRINT() fprintf (stderr, "%s: ", __func__) +# define FUNCTION_PRINT() fprintf (stderr, "%s: ", __func__) /*------. | NLS. | `------*/ -#include +# include -#include -#define _(Msgid) gettext (Msgid) -#define N_(Msgid) (Msgid) +# include +# define _(Msgid) gettext (Msgid) +# define N_(Msgid) (Msgid) /*-----------. | Booleans. | `-----------*/ -#include +# include @@ -148,43 +148,43 @@ typedef size_t uintptr_t; For now, we use assert but we call it aver throughout Bison in case we later wish to try another scheme. */ -#include -#define aver assert +# include +# define aver assert /*-----------. | Obstacks. | `-----------*/ -#define obstack_chunk_alloc xmalloc -#define obstack_chunk_free free -#include +# define obstack_chunk_alloc xmalloc +# define obstack_chunk_free free +# include -#define obstack_sgrow(Obs, Str) \ +# define obstack_sgrow(Obs, Str) \ obstack_grow (Obs, Str, strlen (Str)) -#define obstack_fgrow1(Obs, Format, Arg1) \ +# define obstack_fgrow1(Obs, Format, Arg1) \ do { \ char buf[4096]; \ sprintf (buf, Format, Arg1); \ obstack_grow (Obs, buf, strlen (buf)); \ } while (0) -#define obstack_fgrow2(Obs, Format, Arg1, Arg2) \ +# define obstack_fgrow2(Obs, Format, Arg1, Arg2) \ do { \ char buf[4096]; \ sprintf (buf, Format, Arg1, Arg2); \ obstack_grow (Obs, buf, strlen (buf)); \ } while (0) -#define obstack_fgrow3(Obs, Format, Arg1, Arg2, Arg3) \ +# define obstack_fgrow3(Obs, Format, Arg1, Arg2, Arg3) \ do { \ char buf[4096]; \ sprintf (buf, Format, Arg1, Arg2, Arg3); \ obstack_grow (Obs, buf, strlen (buf)); \ } while (0) -#define obstack_fgrow4(Obs, Format, Arg1, Arg2, Arg3, Arg4) \ +# define obstack_fgrow4(Obs, Format, Arg1, Arg2, Arg3, Arg4) \ do { \ char buf[4096]; \ sprintf (buf, Format, Arg1, Arg2, Arg3, Arg4); \ @@ -197,17 +197,17 @@ do { \ | Extensions to use for the output files. | `-----------------------------------------*/ -#ifndef OUTPUT_EXT -# define OUTPUT_EXT ".output" -#endif +# ifndef OUTPUT_EXT +# define OUTPUT_EXT ".output" +# endif -#ifndef TAB_EXT -# define TAB_EXT ".tab" -#endif +# ifndef TAB_EXT +# define TAB_EXT ".tab" +# endif -#ifndef DEFAULT_TMPDIR -# define DEFAULT_TMPDIR "/tmp" -#endif +# ifndef DEFAULT_TMPDIR +# define DEFAULT_TMPDIR "/tmp" +# endif @@ -215,7 +215,7 @@ do { \ | Free a linked list. | `---------------------*/ -#define LIST_FREE(Type, List) \ +# define LIST_FREE(Type, List) \ do { \ Type *_node, *_next; \ for (_node = List; _node; _node = _next) \ From 62e5fc6ac9bd59f801ca43e7eb81d19960f3e306 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Fri, 30 Mar 2012 13:41:01 +0200 Subject: [PATCH 06/14] gnulib: update. --- gnulib | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnulib b/gnulib index 4730c3e3..0e9d9267 160000 --- a/gnulib +++ b/gnulib @@ -1 +1 @@ -Subproject commit 4730c3e3692b344effb72d46b3ff92db0bdb797a +Subproject commit 0e9d9267fa36c5493b36c0a2b2e422da101ee4b4 From e85056ef5fe3ddf7563a217b941c27de7d7b3cb5 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Tue, 27 Mar 2012 16:20:34 +0200 Subject: [PATCH 07/14] build: simplify and improve the compiler warnings for tests. * configure.ac (warn_common, warn_c, warn_cxx): New. Use them to compute independently the options supported by the C and C++ compilers. Don't AC_SUBST the variables passed to gl_WARN_ADD: it does it for us. (WARN_CFLAGS_TEST, WARN_CXXFLAGS_TEST): Don't aggregate $WARN_CFLAGS and $WARN_CXXFLAGS in them now, leave it to atlocal.in. (O0CFLAGS, O0CXXFLAGS): Move their definition to... * tests/atlocal.in: here. Be more systematic between C and C++. Reorder to factor between variables. Propagate all of the variables when --compile-c-with-cxx. --- configure.ac | 46 ++++++++++++++++++++++-------------------- tests/atlocal.in | 52 +++++++++++++++++++++++++++++------------------- 2 files changed, 55 insertions(+), 43 deletions(-) diff --git a/configure.ac b/configure.ac index 1fffa67c..78f641d3 100644 --- a/configure.ac +++ b/configure.ac @@ -53,6 +53,7 @@ AC_CONFIG_HEADERS([lib/config.h:lib/config.hin]) # Checks for the compiler. AC_PROG_CC_STDC +AC_PROG_CXX # Gnulib (early checks). gl_EARLY @@ -65,31 +66,36 @@ AC_ARG_ENABLE([gcc-warnings], esac], [enable_gcc_warnings=no]) if test "$enable_gcc_warnings" = yes; then + warn_common='-Wall -Wextra -Wno-sign-compare -Wcast-align + -Wcast-qual -Wformat -Wpointer-arith -Wwrite-strings' + warn_c='-Wbad-function-cast -Wmissing-declarations -Wmissing-prototypes + -Wshadow -Wstrict-prototypes' + warn_cxx='' + AC_LANG_PUSH([C]) + for i in $warn_common $warn_c; + do + gl_WARN_ADD([$i], [WARN_CFLAGS]) + done gl_WARN_ADD([-Werror], [WERROR_CFLAGS]) - AC_SUBST([WERROR_CFLAGS]) - gl_WARN_ADD([-Wall]) - gl_WARN_ADD([-Wextra -Wno-sign-compare]) - gl_WARN_ADD([-Wcast-align]) - gl_WARN_ADD([-Wcast-qual]) - gl_WARN_ADD([-Wformat]) - gl_WARN_ADD([-Wpointer-arith]) - gl_WARN_ADD([-Wwrite-strings]) - AC_SUBST([WARN_CXXFLAGS], [$WARN_CFLAGS]) - # The following warnings are not suitable for C++. - gl_WARN_ADD([-Wbad-function-cast]) - gl_WARN_ADD([-Wmissing-declarations]) - gl_WARN_ADD([-Wmissing-prototypes]) - gl_WARN_ADD([-Wshadow]) - gl_WARN_ADD([-Wstrict-prototypes]) - AC_SUBST([WARN_CFLAGS]) # Warnings for the test suite only. gl_WARN_ADD([-Wundef], [WARN_CFLAGS_TEST]) gl_WARN_ADD([-pedantic], [WARN_CFLAGS_TEST]) - AC_SUBST([WARN_CXXFLAGS_TEST], ["$WARN_CXXFLAGS $WARN_CFLAGS_TEST"]) - AC_SUBST([WARN_CFLAGS_TEST], ["$WARN_CFLAGS $WARN_CFLAGS_TEST"]) + AC_LANG_POP([C]) + + AC_LANG_PUSH([C++]) + for i in $warn_common $warn_cxx; + do + gl_WARN_ADD([$i], [WARN_CXXFLAGS]) + done + gl_WARN_ADD([-Werror], [WERROR_CXXFLAGS]) + # Warnings for the test suite only. + gl_WARN_ADD([-Wundef], [WARN_CXXFLAGS_TEST]) + gl_WARN_ADD([-pedantic], [WARN_CXXFLAGS_TEST]) + AC_LANG_POP([C++]) fi BISON_TEST_FOR_WORKING_C_COMPILER +BISON_TEST_FOR_WORKING_CXX_COMPILER AC_ARG_ENABLE([yacc], [AC_HELP_STRING([--disable-yacc], @@ -155,13 +161,9 @@ AC_CONFIG_TESTDIR(tests) AC_CONFIG_FILES([tests/Makefile tests/atlocal]) AC_CONFIG_FILES([tests/bison], [chmod +x tests/bison]) AC_CHECK_PROGS([VALGRIND], [valgrind]) -AC_PROG_CXX -BISON_TEST_FOR_WORKING_CXX_COMPILER AM_MISSING_PROG([AUTOM4TE], [autom4te]) # Needed by tests/atlocal.in. AC_SUBST([GCC]) -AC_SUBST([O0CFLAGS], [`echo $CFLAGS | sed 's/-O[[0-9]] *//'`]) -AC_SUBST([O0CXXFLAGS], [`echo $CXXFLAGS | sed 's/-O[[0-9]] *//'`]) gt_JAVACOMP([1.3]) gt_JAVAEXEC diff --git a/tests/atlocal.in b/tests/atlocal.in index 11554b33..72a9bf75 100644 --- a/tests/atlocal.in +++ b/tests/atlocal.in @@ -16,30 +16,47 @@ # You should have received a copy of the GNU General Public License # along with this program. If not, see . -# We need a C compiler. -: ${CC='@CC@'} - -# We want no optimization. -CFLAGS='@O0CFLAGS@ @WARN_CFLAGS_TEST@ @WERROR_CFLAGS@' - -# Sometimes a test group needs to ignore gcc warnings, so it locally -# sets CFLAGS to this. -NO_WERROR_CFLAGS='@O0CFLAGS@ @WARN_CFLAGS_TEST@' - # We need `config.h'. CPPFLAGS="-I$abs_top_builddir/lib @CPPFLAGS@" +## ------------------- ## +## C/C++ Compilation. ## +## ------------------- ## + +: ${CC='@CC@'} +: ${CXX='@CXX@'} + # Is the compiler GCC? GCC='@GCC@' -# The C++ compiler. -: ${CXX='@CXX@'} +# We want no optimization. + O0CFLAGS=`echo '@CFLAGS@' | sed 's/-O[0-9] *//'` +O0CXXFLAGS=`echo '@CXXFLAGS@' | sed 's/-O[0-9] *//'` + +# Sometimes a test group needs to ignore gcc warnings, so it locally +# sets CFLAGS to this. + NO_WERROR_CFLAGS="$O0CFLAGS @WARN_CFLAGS@ @WARN_CFLAGS_TEST@" +NO_WERROR_CXXFLAGS="$O0CXXFLAGS @WARN_CXXFLAGS@ @WARN_CXXFLAGS_TEST@" + +# But most of the time, we want -Werror. + CFLAGS="$NO_WERROR_CFLAGS @WERROR_CFLAGS@" +CXXFLAGS="$NO_WERROR_CXXFLAGS @WERROR_CXXFLAGS@" # If 'exit 77'; skip all C++ tests; otherwise ':'. BISON_CXX_WORKS='@BISON_CXX_WORKS@' -# We want no optimization with C++, too. -CXXFLAGS='@O0CXXFLAGS@ @WARN_CXXFLAGS_TEST@ @WERROR_CFLAGS@' +# Handle --compile-c-with-cxx here, once CXX and CXXFLAGS are known. +if "$at_arg_compile_c_with_cxx"; then + CC=$CXX + O0CFLAGS=$O0CXXFLAGS + NO_WERROR_CFLAGS=$NO_WERROR_CXXFLAGS + CFLAGS=$CXXFLAGS +fi + + +## ------- ## +## Other. ## +## ------- ## # Are special link options needed? LDFLAGS='@LDFLAGS@' @@ -62,10 +79,3 @@ CONF_JAVA='@CONF_JAVA@' # Use simple quotes (lib/quote.c). LC_CTYPE=C export LC_CTYPE - - -# Handle --compile-c-with-cxx here, once CXX and CXXFLAGS are known. -if "$at_arg_compile_c_with_cxx"; then - CC=$CXX - CFLAGS=$CXXFLAGS -fi From ef51bfa744db744dc4b2eff1ba9d6334c807f8e6 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Fri, 30 Mar 2012 15:50:45 +0200 Subject: [PATCH 08/14] c++: use nullptr for C++11. C++11 introduces "nullptr" which plays the role of C's NULL, in replacement of "0". Fix the C++ skeletons to avoid warnings about uses of "0" in place of "nullptr", and improve C skeletons to also use this "nullptr" when compiled with a C++11 compiler. * configure.ac: More C++ warnings. * NEWS (2.5.1): Document this. * data/c++.m4, data/c.m4 (b4_null_define): New. (b4_null): Use YY_NULL instead of 0. * data/glr.c, data/lalr1.cc, data/location.cc, data/yacc.c: Call b4_null_define/b4_null where appropriate. Use YY_NULL instead of NULL. * data/location.cc (initialize): Accept a default argument, YY_NULL. * tests/actions.at, tests/calc.at: Adjust. * data/glr.c, lib/libiberty.h, src/system.h (__attribute__): Do not disable it when __STRICT_ANSI__ is defined, as, for instance, it disables the __attribute__((unused)) which protects us from some compiler warnings. This was already done elsewhere in Bison, in 2001, see 4a0d89369599a2cea01f4fbdf791f426a02cb5a3. * tests/regression.at: Adjust output. --- NEWS | 8 +++ configure.ac | 2 +- data/c++.m4 | 2 + data/c.m4 | 25 ++++++++-- data/glr.c | 115 ++++++++++++++++++++++---------------------- data/lalr1.cc | 4 +- data/location.cc | 10 ++-- data/yacc.c | 2 + lib/libiberty.h | 2 +- src/system.h | 2 +- tests/actions.at | 2 +- tests/calc.at | 2 +- tests/regression.at | 2 +- 13 files changed, 105 insertions(+), 73 deletions(-) diff --git a/NEWS b/NEWS index 838a6868..d972d85d 100644 --- a/NEWS +++ b/NEWS @@ -9,6 +9,9 @@ Bison News tools such as diff, warning messages from the test suite itself, etc. + __attribute__ is not longer disabled when __STRICT_ANSI__ is defined + (i.e., when -std is passed to GCC). + ** Warnings during the build procedure have been eliminated. ** Many minor improvements have been made to the manual: @@ -26,6 +29,11 @@ Bison News The Java parser no longer throws ArrayIndexOutOfBoundsException if the first token leads to a syntax error. Some minor clean ups. +** C++11 compatibility: + + C and C++ parsers use nullptr instead of 0 when __cplusplus is + 201103L or higher. + * Changes in version 2.5 (2011-05-14): ** Grammar symbol names can now contain non-initial dashes: diff --git a/configure.ac b/configure.ac index 78f641d3..210002b2 100644 --- a/configure.ac +++ b/configure.ac @@ -70,7 +70,7 @@ if test "$enable_gcc_warnings" = yes; then -Wcast-qual -Wformat -Wpointer-arith -Wwrite-strings' warn_c='-Wbad-function-cast -Wmissing-declarations -Wmissing-prototypes -Wshadow -Wstrict-prototypes' - warn_cxx='' + warn_cxx='-Wnoexcept -Wzero-as-null-pointer-constant' AC_LANG_PUSH([C]) for i in $warn_common $warn_c; do diff --git a/data/c++.m4 b/data/c++.m4 index 8470ebe9..9913a172 100644 --- a/data/c++.m4 +++ b/data/c++.m4 @@ -97,6 +97,8 @@ m4_map_sep([ b4_token_enum], [, ]) + + ## ----------------- ## ## Semantic Values. ## ## ----------------- ## diff --git a/data/c.m4 b/data/c.m4 index e0e58cdb..195c441d 100644 --- a/data/c.m4 +++ b/data/c.m4 @@ -146,16 +146,31 @@ m4_define([b4_table_value_equals], [[YYID (0)]], [[((]$2[) == (]$3[))]])]) + ## ---------## ## Values. ## ## ---------## -# b4_null ---------- -# Return a null pointer constant. NULL infringes on the user name -# space in C, so use 0 rather than NULL. -m4_define([b4_null], [0]) +# b4_null_define +# -------------- +# Portability issues: define a YY_NULL appropriate for the current +# language (C, C++98, or C++11). +m4_define([b4_null_define], +[# ifndef YY_NULL +# if defined __cplusplus && 201103L <= __cplusplus +# define YY_NULL nullptr +# else +# define YY_NULL 0 +# endif +# endif[]dnl +]) + + +# b4_null +# ------- +# Return a null pointer constant. +m4_define([b4_null], [YY_NULL]) diff --git a/data/glr.c b/data/glr.c index 17eff387..89fbe101 100644 --- a/data/glr.c +++ b/data/glr.c @@ -171,6 +171,8 @@ m4_if(b4_prefix, [yy], [], /* Copy the first part of user declarations. */ ]b4_user_pre_prologue +b4_null_define + dnl # b4_shared_declarations dnl # ---------------------- dnl # Declaration that might either go into the header (if --defines) @@ -310,8 +312,7 @@ b4_percent_code_get[]dnl #ifndef __attribute__ /* This feature is available in gcc versions 2.5 and later. */ # if (! defined __GNUC__ || __GNUC__ < 2 \ - || (__GNUC__ == 2 && __GNUC_MINOR__ < 5) \ - || (defined __STRICT_ANSI__ && __STRICT_ANSI__)) + || (__GNUC__ == 2 && __GNUC_MINOR__ < 5)) # define __attribute__(Spec) /* empty */ # endif #endif @@ -827,7 +828,7 @@ static void yyFail (yyGLRStack* yystackp]b4_pure_formals[, const char* yymsg) static void yyFail (yyGLRStack* yystackp]b4_pure_formals[, const char* yymsg) { - if (yymsg != NULL) + if (yymsg != YY_NULL) yyerror (]b4_yyerror_args[yymsg); YYLONGJMP (yystackp->yyexception_buffer, 1); } @@ -901,7 +902,7 @@ yyuserAction (yyRuleNum yyn, int yyrhslen, yyGLRStackItem* yyvsp, ]b4_user_formals[) { yybool yynormal __attribute__ ((__unused__)) = - (yystackp->yysplitPoint == NULL); + (yystackp->yysplitPoint == YY_NULL); int yylow; ]b4_parse_param_use[]dnl [# undef yyerrok @@ -988,7 +989,7 @@ yydestroyGLRState (char const *yymsg, yyGLRState *yys]b4_user_formals[) else YYFPRINTF (stderr, "%s incomplete ", yymsg); yy_symbol_print (stderr, yystos[yys->yylrState], - NULL]b4_locations_if([, &yys->yyloc])[]b4_user_args[); + YY_NULL]b4_locations_if([, &yys->yyloc])[]b4_user_args[); YYFPRINTF (stderr, "\n"); } #endif @@ -1141,7 +1142,7 @@ yyinitStateSet (yyGLRStateSet* yyset) yyset->yystates = (yyGLRState**) YYMALLOC (16 * sizeof yyset->yystates[0]); if (! yyset->yystates) return yyfalse; - yyset->yystates[0] = NULL; + yyset->yystates[0] = YY_NULL; yyset->yylookaheadNeeds = (yybool*) YYMALLOC (16 * sizeof yyset->yylookaheadNeeds[0]); if (! yyset->yylookaheadNeeds) @@ -1171,8 +1172,8 @@ yyinitGLRStack (yyGLRStack* yystackp, size_t yysize) if (!yystackp->yyitems) return yyfalse; yystackp->yynextFree = yystackp->yyitems; - yystackp->yysplitPoint = NULL; - yystackp->yylastDeleted = NULL; + yystackp->yysplitPoint = YY_NULL; + yystackp->yylastDeleted = YY_NULL; return yyinitStateSet (&yystackp->yytops); } @@ -1211,10 +1212,10 @@ yyexpandGLRStack (yyGLRStack* yystackp) { yyGLRState* yys0 = &yyp0->yystate; yyGLRState* yys1 = &yyp1->yystate; - if (yys0->yypred != NULL) + if (yys0->yypred != YY_NULL) yys1->yypred = YYRELOC (yyp0, yyp1, yys0->yypred, yystate); - if (! yys0->yyresolved && yys0->yysemantics.yyfirstVal != NULL) + if (! yys0->yyresolved && yys0->yysemantics.yyfirstVal != YY_NULL) yys1->yysemantics.yyfirstVal = YYRELOC(yyp0, yyp1, yys0->yysemantics.yyfirstVal, yyoption); } @@ -1222,18 +1223,18 @@ yyexpandGLRStack (yyGLRStack* yystackp) { yySemanticOption* yyv0 = &yyp0->yyoption; yySemanticOption* yyv1 = &yyp1->yyoption; - if (yyv0->yystate != NULL) + if (yyv0->yystate != YY_NULL) yyv1->yystate = YYRELOC (yyp0, yyp1, yyv0->yystate, yystate); - if (yyv0->yynext != NULL) + if (yyv0->yynext != YY_NULL) yyv1->yynext = YYRELOC (yyp0, yyp1, yyv0->yynext, yyoption); } } - if (yystackp->yysplitPoint != NULL) + if (yystackp->yysplitPoint != YY_NULL) yystackp->yysplitPoint = YYRELOC (yystackp->yyitems, yynewItems, yystackp->yysplitPoint, yystate); for (yyn = 0; yyn < yystackp->yytops.yysize; yyn += 1) - if (yystackp->yytops.yystates[yyn] != NULL) + if (yystackp->yytops.yystates[yyn] != YY_NULL) yystackp->yytops.yystates[yyn] = YYRELOC (yystackp->yyitems, yynewItems, yystackp->yytops.yystates[yyn], yystate); @@ -1257,7 +1258,7 @@ yyfreeGLRStack (yyGLRStack* yystackp) static inline void yyupdateSplit (yyGLRStack* yystackp, yyGLRState* yys) { - if (yystackp->yysplitPoint != NULL && yystackp->yysplitPoint > yys) + if (yystackp->yysplitPoint != YY_NULL && yystackp->yysplitPoint > yys) yystackp->yysplitPoint = yys; } @@ -1265,9 +1266,9 @@ yyupdateSplit (yyGLRStack* yystackp, yyGLRState* yys) static inline void yymarkStackDeleted (yyGLRStack* yystackp, size_t yyk) { - if (yystackp->yytops.yystates[yyk] != NULL) + if (yystackp->yytops.yystates[yyk] != YY_NULL) yystackp->yylastDeleted = yystackp->yytops.yystates[yyk]; - yystackp->yytops.yystates[yyk] = NULL; + yystackp->yytops.yystates[yyk] = YY_NULL; } /** Undelete the last stack that was marked as deleted. Can only be @@ -1276,12 +1277,12 @@ yymarkStackDeleted (yyGLRStack* yystackp, size_t yyk) static void yyundeleteLastStack (yyGLRStack* yystackp) { - if (yystackp->yylastDeleted == NULL || yystackp->yytops.yysize != 0) + if (yystackp->yylastDeleted == YY_NULL || yystackp->yytops.yysize != 0) return; yystackp->yytops.yystates[0] = yystackp->yylastDeleted; yystackp->yytops.yysize = 1; YYDPRINTF ((stderr, "Restoring last deleted stack as stack #0.\n")); - yystackp->yylastDeleted = NULL; + yystackp->yylastDeleted = YY_NULL; } static inline void @@ -1291,7 +1292,7 @@ yyremoveDeletes (yyGLRStack* yystackp) yyi = yyj = 0; while (yyj < yystackp->yytops.yysize) { - if (yystackp->yytops.yystates[yyi] == NULL) + if (yystackp->yytops.yystates[yyi] == YY_NULL) { if (yyi == yyj) { @@ -1353,7 +1354,7 @@ yyglrShiftDefer (yyGLRStack* yystackp, size_t yyk, yyStateNum yylrState, yynewState->yyposn = yyposn; yynewState->yyresolved = yyfalse; yynewState->yypred = yystackp->yytops.yystates[yyk]; - yynewState->yysemantics.yyfirstVal = NULL; + yynewState->yysemantics.yyfirstVal = YY_NULL; yystackp->yytops.yystates[yyk] = yynewState; /* Invokes YY_RESERVE_GLRSTACK. */ @@ -1372,7 +1373,7 @@ yydoAction (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, { int yynrhs = yyrhsLength (yyrule); - if (yystackp->yysplitPoint == NULL) + if (yystackp->yysplitPoint == YY_NULL) { /* Standard special case: single stack. */ yyGLRStackItem* rhs = (yyGLRStackItem*) yystackp->yytops.yystates[yyk]; @@ -1428,7 +1429,7 @@ yy_reduce_print (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, { int yynrhs = yyrhsLength (yyrule); yybool yynormal __attribute__ ((__unused__)) = - (yystackp->yysplitPoint == NULL); + (yystackp->yysplitPoint == YY_NULL); yyGLRStackItem* yyvsp = (yyGLRStackItem*) yystackp->yytops.yystates[yyk]; int yylow = 1; int yyi; @@ -1468,7 +1469,7 @@ yyglrReduce (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, { size_t yyposn = yystackp->yytops.yystates[yyk]->yyposn; - if (yyforceEval || yystackp->yysplitPoint == NULL) + if (yyforceEval || yystackp->yysplitPoint == YY_NULL) { YYSTYPE yysval; YYLTYPE yyloc; @@ -1501,7 +1502,7 @@ yyglrReduce (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, "Reduced stack %lu by rule #%d; action deferred. Now in state %d.\n", (unsigned long int) yyk, yyrule - 1, yynewLRState)); for (yyi = 0; yyi < yystackp->yytops.yysize; yyi += 1) - if (yyi != yyk && yystackp->yytops.yystates[yyi] != NULL) + if (yyi != yyk && yystackp->yytops.yystates[yyi] != YY_NULL) { yyGLRState* yyp, *yysplit = yystackp->yysplitPoint; yyp = yystackp->yytops.yystates[yyi]; @@ -1528,7 +1529,7 @@ yyglrReduce (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, static size_t yysplitStack (yyGLRStack* yystackp, size_t yyk) { - if (yystackp->yysplitPoint == NULL) + if (yystackp->yysplitPoint == YY_NULL) { YYASSERT (yyk == 0); yystackp->yysplitPoint = yystackp->yytops.yystates[yyk]; @@ -1538,7 +1539,7 @@ yysplitStack (yyGLRStack* yystackp, size_t yyk) yyGLRState** yynewStates; yybool* yynewLookaheadNeeds; - yynewStates = NULL; + yynewStates = YY_NULL; if (yystackp->yytops.yycapacity > (YYSIZEMAX / (2 * sizeof yynewStates[0]))) @@ -1549,7 +1550,7 @@ yysplitStack (yyGLRStack* yystackp, size_t yyk) (yyGLRState**) YYREALLOC (yystackp->yytops.yystates, (yystackp->yytops.yycapacity * sizeof yynewStates[0])); - if (yynewStates == NULL) + if (yynewStates == YY_NULL) yyMemoryExhausted (yystackp); yystackp->yytops.yystates = yynewStates; @@ -1557,7 +1558,7 @@ yysplitStack (yyGLRStack* yystackp, size_t yyk) (yybool*) YYREALLOC (yystackp->yytops.yylookaheadNeeds, (yystackp->yytops.yycapacity * sizeof yynewLookaheadNeeds[0])); - if (yynewLookaheadNeeds == NULL) + if (yynewLookaheadNeeds == YY_NULL) yyMemoryExhausted (yystackp); yystackp->yytops.yylookaheadNeeds = yynewLookaheadNeeds; } @@ -1623,9 +1624,9 @@ yymergeOptionSets (yySemanticOption* yyy0, yySemanticOption* yyy1) yyz1 = yys1->yysemantics.yyfirstVal; while (YYID (yytrue)) { - if (yyz1 == *yyz0p || yyz1 == NULL) + if (yyz1 == *yyz0p || yyz1 == YY_NULL) break; - else if (*yyz0p == NULL) + else if (*yyz0p == YY_NULL) { *yyz0p = yyz1; break; @@ -1748,7 +1749,7 @@ yyreportTree (yySemanticOption* yyx, int yyindent) for (yyi = yynrhs, yys = yyx->yystate; 0 < yyi; yyi -= 1, yys = yys->yypred) yystates[yyi] = yys; - if (yys == NULL) + if (yys == YY_NULL) { yyleftmost_state.yyposn = 0; yystates[0] = &yyleftmost_state; @@ -1823,7 +1824,7 @@ yyresolveLocations (yyGLRState* yys1, int yyn1, YYSTYPE yylval_current; YYLTYPE yylloc_current; yyoption = yys1->yysemantics.yyfirstVal; - YYASSERT (yyoption != NULL); + YYASSERT (yyoption != YY_NULL); yynrhs = yyrhsLength (yyoption->yyrule); if (yynrhs > 0) { @@ -1881,7 +1882,7 @@ yyresolveValue (yyGLRState* yys, yyGLRStack* yystackp]b4_user_formals[) yybest = yyoptionList; yymerge = yyfalse; - for (yypp = &yyoptionList->yynext; *yypp != NULL; ) + for (yypp = &yyoptionList->yynext; *yypp != YY_NULL; ) { yySemanticOption* yyp = *yypp; @@ -1924,7 +1925,7 @@ yyresolveValue (yyGLRState* yys, yyGLRStack* yystackp]b4_user_formals[) yyflag = yyresolveAction (yybest, yystackp, &yysval, yylocp]b4_user_args[); if (yyflag == yyok) - for (yyp = yybest->yynext; yyp != NULL; yyp = yyp->yynext) + for (yyp = yybest->yynext; yyp != YY_NULL; yyp = yyp->yynext) { if (yyprec == yydprec[yyp->yyrule]) { @@ -1952,14 +1953,14 @@ yyresolveValue (yyGLRState* yys, yyGLRStack* yystackp]b4_user_formals[) yys->yysemantics.yysval = yysval; } else - yys->yysemantics.yyfirstVal = NULL; + yys->yysemantics.yyfirstVal = YY_NULL; return yyflag; } static YYRESULTTAG yyresolveStack (yyGLRStack* yystackp]b4_user_formals[) { - if (yystackp->yysplitPoint != NULL) + if (yystackp->yysplitPoint != YY_NULL) { yyGLRState* yys; int yyn; @@ -1979,10 +1980,10 @@ yycompressStack (yyGLRStack* yystackp) { yyGLRState* yyp, *yyq, *yyr; - if (yystackp->yytops.yysize != 1 || yystackp->yysplitPoint == NULL) + if (yystackp->yytops.yysize != 1 || yystackp->yysplitPoint == YY_NULL) return; - for (yyp = yystackp->yytops.yystates[0], yyq = yyp->yypred, yyr = NULL; + for (yyp = yystackp->yytops.yystates[0], yyq = yyp->yypred, yyr = YY_NULL; yyp != yystackp->yysplitPoint; yyr = yyp, yyp = yyq, yyq = yyp->yypred) yyp->yypred = yyr; @@ -1990,10 +1991,10 @@ yycompressStack (yyGLRStack* yystackp) yystackp->yyspaceLeft += yystackp->yynextFree - yystackp->yyitems; yystackp->yynextFree = ((yyGLRStackItem*) yystackp->yysplitPoint) + 1; yystackp->yyspaceLeft -= yystackp->yynextFree - yystackp->yyitems; - yystackp->yysplitPoint = NULL; - yystackp->yylastDeleted = NULL; + yystackp->yysplitPoint = YY_NULL; + yystackp->yylastDeleted = YY_NULL; - while (yyr != NULL) + while (yyr != YY_NULL) { yystackp->yynextFree->yystate = *yyr; yyr = yyr->yypred; @@ -2012,7 +2013,7 @@ yyprocessOneStack (yyGLRStack* yystackp, size_t yyk, const short int* yyconflicts; yyRuleNum yyrule; - while (yystackp->yytops.yystates[yyk] != NULL) + while (yystackp->yytops.yystates[yyk] != YY_NULL) { yyStateNum yystate = yystackp->yytops.yystates[yyk]->yylrState; YYDPRINTF ((stderr, "Stack %lu Entering state %d\n", @@ -2094,14 +2095,14 @@ yyreportSyntaxError (yyGLRStack* yystackp]b4_user_formals[) yyerror (]b4_lyyerror_args[YY_("syntax error")); #else yySymbol yytoken = yychar == YYEMPTY ? YYEMPTY : YYTRANSLATE (yychar); - size_t yysize0 = yytnamerr (NULL, yytokenName (yytoken)); + size_t yysize0 = yytnamerr (YY_NULL, yytokenName (yytoken)); size_t yysize = yysize0; size_t yysize1; yybool yysize_overflow = yyfalse; - char* yymsg = NULL; + char* yymsg = YY_NULL; enum { YYERROR_VERBOSE_ARGS_MAXIMUM = 5 }; /* Internationalized format string. */ - const char *yyformat = 0; + const char *yyformat = YY_NULL; /* Arguments of yyformat. */ char const *yyarg[YYERROR_VERBOSE_ARGS_MAXIMUM]; /* Number of reported tokens (one for the "unexpected", one per @@ -2156,7 +2157,7 @@ yyreportSyntaxError (yyGLRStack* yystackp]b4_user_formals[) break; } yyarg[yycount++] = yytokenName (yyx); - yysize1 = yysize + yytnamerr (NULL, yytokenName (yyx)); + yysize1 = yysize + yytnamerr (YY_NULL, yytokenName (yyx)); yysize_overflow |= yysize1 < yysize; yysize = yysize1; } @@ -2230,7 +2231,7 @@ yyrecoverSyntaxError (yyGLRStack* yystackp]b4_user_formals[) { yySymbol yytoken; if (yychar == YYEOF) - yyFail (yystackp][]b4_lpure_args[, NULL); + yyFail (yystackp][]b4_lpure_args[, YY_NULL); if (yychar != YYEMPTY) {]b4_locations_if([[ /* We throw away the lookahead, but the error range @@ -2271,10 +2272,10 @@ yyrecoverSyntaxError (yyGLRStack* yystackp]b4_user_formals[) /* Reduce to one stack. */ for (yyk = 0; yyk < yystackp->yytops.yysize; yyk += 1) - if (yystackp->yytops.yystates[yyk] != NULL) + if (yystackp->yytops.yystates[yyk] != YY_NULL) break; if (yyk >= yystackp->yytops.yysize) - yyFail (yystackp][]b4_lpure_args[, NULL); + yyFail (yystackp][]b4_lpure_args[, YY_NULL); for (yyk += 1; yyk < yystackp->yytops.yysize; yyk += 1) yymarkStackDeleted (yystackp, yyk); yyremoveDeletes (yystackp); @@ -2282,7 +2283,7 @@ yyrecoverSyntaxError (yyGLRStack* yystackp]b4_user_formals[) /* Now pop stack until we find a state that shifts the error token. */ yystackp->yyerrState = 3; - while (yystackp->yytops.yystates[0] != NULL) + while (yystackp->yytops.yystates[0] != YY_NULL) { yyGLRState *yys = yystackp->yytops.yystates[0]; yyj = yypact[yys->yylrState]; @@ -2305,14 +2306,14 @@ yyrecoverSyntaxError (yyGLRStack* yystackp]b4_user_formals[) } } ]b4_locations_if([[ yystackp->yyerror_range[1].yystate.yyloc = yys->yyloc;]])[ - if (yys->yypred != NULL) + if (yys->yypred != YY_NULL) yydestroyGLRState ("Error: popping", yys]b4_user_args[); yystackp->yytops.yystates[0] = yys->yypred; yystackp->yynextFree -= 1; yystackp->yyspaceLeft += 1; } - if (yystackp->yytops.yystates[0] == NULL) - yyFail (yystackp][]b4_lpure_args[, NULL); + if (yystackp->yytops.yystates[0] == YY_NULL) + yyFail (yystackp][]b4_lpure_args[, YY_NULL); } #define YYCHK1(YYE) \ @@ -2564,7 +2565,7 @@ m4_popdef([b4_at_dollar])])dnl { yyGLRState *yys = yystates[yyk]; ]b4_locations_if([[ yystack.yyerror_range[1].yystate.yyloc = yys->yyloc;]] -)[ if (yys->yypred != NULL) +)[ if (yys->yypred != YY_NULL) yydestroyGLRState ("Cleanup: popping", yys]b4_user_args[); yystates[yyk] = yys->yypred; yystack.yynextFree -= 1; @@ -2601,7 +2602,7 @@ yy_yypstack (yyGLRState* yys) static void yypstates (yyGLRState* yyst) { - if (yyst == NULL) + if (yyst == YY_NULL) YYFPRINTF (stderr, ""); else yy_yypstack (yyst); @@ -2615,7 +2616,7 @@ yypstack (yyGLRStack* yystackp, size_t yyk) } #define YYINDEX(YYX) \ - ((YYX) == NULL ? -1 : (yyGLRStackItem*) (YYX) - yystackp->yyitems) + ((YYX) == YY_NULL ? -1 : (yyGLRStackItem*) (YYX) - yystackp->yyitems) static void diff --git a/data/lalr1.cc b/data/lalr1.cc index 6f55e187..dc0cc8cc 100644 --- a/data/lalr1.cc +++ b/data/lalr1.cc @@ -51,6 +51,8 @@ dnl FIXME: This is wrong, we want computed header guards. ]b4_percent_define_ifdef([[location_type]], [], [[#include "location.hh"]])[ +]b4_null_define[ + /* Enabling traces. */ #ifndef YYDEBUG # define YYDEBUG ]b4_debug_flag[ @@ -931,7 +933,7 @@ b4_error_verbose_if([int yystate, int yytoken], } } - char const* yyformat = 0; + char const* yyformat = YY_NULL; switch (yycount) { #define YYCASE_(N, S) \ diff --git a/data/location.cc b/data/location.cc index d264d275..f4fc9cc5 100644 --- a/data/location.cc +++ b/data/location.cc @@ -20,7 +20,7 @@ m4_changecom() m4_divert_push(0)dnl @output(b4_dir_prefix[]position.hh@)@ b4_copyright([Positions for Bison parsers in C++], - [2002-2007, 2009-2011])[ + [2002-2007, 2009-2012])[ /** ** \file position.hh @@ -34,6 +34,8 @@ b4_copyright([Positions for Bison parsers in C++], # include # include +]b4_null_define[ + ]b4_namespace_open[ /// Abstract a position. class position @@ -42,13 +44,13 @@ b4_copyright([Positions for Bison parsers in C++], ]m4_ifdef([b4_location_constructors], [ /// Construct a position. position () - : filename (0), line (]b4_location_initial_line[), column (]b4_location_initial_column[) + : filename (YY_NULL), line (]b4_location_initial_line[), column (]b4_location_initial_column[) { } ])[ /// Initialization. - inline void initialize (]b4_percent_define_get([[filename_type]])[* fn) + inline void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) { filename = fn; line = ]b4_location_initial_line[; @@ -174,7 +176,7 @@ b4_copyright([Locations for Bison parsers in C++], ])[ /// Initialization. - inline void initialize (]b4_percent_define_get([[filename_type]])[* fn) + inline void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) { begin.initialize (fn); end = begin; diff --git a/data/yacc.c b/data/yacc.c index 96eea2a8..8d26479d 100644 --- a/data/yacc.c +++ b/data/yacc.c @@ -267,6 +267,8 @@ m4_if(b4_prefix, [yy], [], /* Copy the first part of user declarations. */ ]b4_user_pre_prologue[ +]b4_null_define[ + /* Enabling traces. */ #ifndef YYDEBUG # define YYDEBUG ]b4_debug_flag[ diff --git a/lib/libiberty.h b/lib/libiberty.h index fdcae40b..ad7b358f 100644 --- a/lib/libiberty.h +++ b/lib/libiberty.h @@ -24,7 +24,7 @@ # define BISON_LIBIBERTY_H_ 1 # ifndef __attribute__ -# if __GNUC__ < 2 || (__GNUC__ == 2 && __GNUC_MINOR__ < 8) || __STRICT_ANSI__ +# if __GNUC__ < 2 || (__GNUC__ == 2 && __GNUC_MINOR__ < 8) # define __attribute__(x) # endif # endif diff --git a/src/system.h b/src/system.h index e3f17d89..d3c544b4 100644 --- a/src/system.h +++ b/src/system.h @@ -85,7 +85,7 @@ typedef size_t uintptr_t; # ifndef __attribute__ /* This feature is available in gcc versions 2.5 and later. */ # if (! defined __GNUC__ || __GNUC__ < 2 \ - || (__GNUC__ == 2 && __GNUC_MINOR__ < 5) || __STRICT_ANSI__) + || (__GNUC__ == 2 && __GNUC_MINOR__ < 5)) # define __attribute__(Spec) /* empty */ # endif # endif diff --git a/tests/actions.at b/tests/actions.at index ed913cd1..bb2201db 100644 --- a/tests/actions.at +++ b/tests/actions.at @@ -345,7 +345,7 @@ thing: ; %% /* Alias to ARGV[1]. */ -const char *source = 0; +const char *source = YY_NULL; static int yylex (]AT_LEX_FORMALS[) diff --git a/tests/calc.at b/tests/calc.at index 455cd72f..c5040083 100644 --- a/tests/calc.at +++ b/tests/calc.at @@ -241,7 +241,7 @@ int yylex (]AT_LEX_FORMALS[); are stored in a union, from which objects with constructors are excluded in C++. */ %initial-action { - @$.initialize (0); + @$.initialize (); } ])])[ diff --git a/tests/regression.at b/tests/regression.at index 90ea6497..584c541b 100644 --- a/tests/regression.at +++ b/tests/regression.at @@ -769,7 +769,7 @@ static const yytype_uint8 yyrline[] = static const char *const yytname[] = { "$end", "error", "$undefined", "\"if\"", "\"const\"", "\"then\"", - "\"else\"", "$accept", "statement", "struct_stat", "if", "else", 0 + "\"else\"", "$accept", "statement", "struct_stat", "if", "else", YY_NULL }; static const yytype_uint16 yytoknum[] = { From 769a8ef9bcb5e14d0be9d0869f5dca20ab093930 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Sat, 31 Mar 2012 09:45:59 +0200 Subject: [PATCH 09/14] glr: do not use locations when they are not requested When the test suite runs with -O2 and warnings enabled, G++ complains of locations being used, but not initialized. The simplest is to not use locations. * data/glr.c (b4_locuser_formals, b4_locuser_args): New. Use them when locations should not be used. Use b4_locations_if where appropriate. (yyuserAction): Modify the order to the arguments to make it more alike the other routines, and to make use of b4_locuser_args simpler. --- data/glr.c | 150 ++++++++++++++++++++++++++++------------------------- 1 file changed, 78 insertions(+), 72 deletions(-) diff --git a/data/glr.c b/data/glr.c index 89fbe101..65107d9a 100644 --- a/data/glr.c +++ b/data/glr.c @@ -93,13 +93,27 @@ m4_define([b4_lpure_args], [b4_pure_if([b4_locations_if([, &yylloc])])[]b4_user_args]) + # b4_pure_formals # --------------- -# Arguments passed to yyerror: user formals plus yylocp. +# Arguments passed to yyerror: user formals plus yylocp with leading comma. m4_define([b4_pure_formals], [b4_pure_if([b4_locations_if([, YYLTYPE *yylocp])])[]b4_user_formals]) +# b4_locuser_formals(LOC = yylocp) +# -------------------------------- +m4_define([b4_locuser_formals], +[b4_locations_if([, YYLTYPE *m4_default([$1], [yylocp])])[]b4_user_formals]) + + +# b4_locuser_args(LOC = yylocp) +# ----------------------------- +m4_define([b4_locuser_args], +[b4_locations_if([, m4_default([$1], [yylocp])])[]b4_user_args]) + + + ## ----------------- ## ## Semantic Values. ## ## ----------------- ## @@ -582,15 +596,14 @@ do { \ ]b4_yy_symbol_print_generate([b4_c_ansi_function_def])[ -# define YY_SYMBOL_PRINT(Title, Type, Value, Location) \ -do { \ - if (yydebug) \ - { \ - YYFPRINTF (stderr, "%s ", Title); \ - yy_symbol_print (stderr, Type, \ - Value]b4_locations_if([, Location])[]b4_user_args[); \ - YYFPRINTF (stderr, "\n"); \ - } \ +# define YY_SYMBOL_PRINT(Title, Type, Value, Location) \ +do { \ + if (yydebug) \ + { \ + YYFPRINTF (stderr, "%s ", Title); \ + yy_symbol_print (stderr, Type, Value]b4_locuser_args([Location])[); \ + YYFPRINTF (stderr, "\n"); \ + } \ } while (YYID (0)) /* Nonzero means print parse trace. It is left uninitialized so that @@ -896,10 +909,8 @@ yyfill (yyGLRStackItem *yyvsp, int *yylow, int yylow1, yybool yynormal) * yyerr for YYERROR, yyabort for YYABORT. */ /*ARGSUSED*/ static YYRESULTTAG yyuserAction (yyRuleNum yyn, int yyrhslen, yyGLRStackItem* yyvsp, - YYSTYPE* yyvalp, - YYLTYPE* YYOPTIONAL_LOC (yylocp), - yyGLRStack* yystackp - ]b4_user_formals[) + yyGLRStack* yystackp, + YYSTYPE* yyvalp]b4_locuser_formals[) { yybool yynormal __attribute__ ((__unused__)) = (yystackp->yysplitPoint == YY_NULL); @@ -928,9 +939,9 @@ yyuserAction (yyRuleNum yyn, int yyrhslen, yyGLRStackItem* yyvsp, if (yyrhslen == 0) *yyvalp = yyval_default; else - *yyvalp = yyvsp[YYFILL (1-yyrhslen)].yystate.yysemantics.yysval; + *yyvalp = yyvsp[YYFILL (1-yyrhslen)].yystate.yysemantics.yysval;]b4_locations_if([[ YYLLOC_DEFAULT ((*yylocp), (yyvsp - yyrhslen), yyrhslen); -]b4_locations_if([[ yystackp->yyerror_range[1].yystate.yyloc = *yylocp; + yystackp->yyerror_range[1].yystate.yyloc = *yylocp; ]])[ switch (yyn) { @@ -978,7 +989,7 @@ yydestroyGLRState (char const *yymsg, yyGLRState *yys]b4_user_formals[) { if (yys->yyresolved) yydestruct (yymsg, yystos[yys->yylrState], - &yys->yysemantics.yysval]b4_locations_if([, &yys->yyloc])[]b4_user_args[); + &yys->yysemantics.yysval]b4_locuser_args([&yys->yyloc])[); else { #if YYDEBUG @@ -989,7 +1000,7 @@ yydestroyGLRState (char const *yymsg, yyGLRState *yys]b4_user_formals[) else YYFPRINTF (stderr, "%s incomplete ", yymsg); yy_symbol_print (stderr, yystos[yys->yylrState], - YY_NULL]b4_locations_if([, &yys->yyloc])[]b4_user_args[); + YY_NULL]b4_locuser_args([&yys->yyloc])[); YYFPRINTF (stderr, "\n"); } #endif @@ -1120,8 +1131,8 @@ yyaddDeferredAction (yyGLRStack* yystackp, size_t yyk, yyGLRState* yystate, if (yystackp->yytops.yylookaheadNeeds[yyk]) { yynewOption->yyrawchar = yychar; - yynewOption->yyval = yylval; - yynewOption->yyloc = yylloc; + yynewOption->yyval = yylval;]b4_locations_if([ + yynewOption->yyloc = yylloc;])[ } else yynewOption->yyrawchar = YYEMPTY; @@ -1326,7 +1337,7 @@ yyremoveDeletes (yyGLRStack* yystackp) static inline void yyglrShift (yyGLRStack* yystackp, size_t yyk, yyStateNum yylrState, size_t yyposn, - YYSTYPE* yyvalp, YYLTYPE* yylocp) + YYSTYPE* yyvalp]b4_locations_if([, YYLTYPE* yylocp])[) { yyGLRState* yynewState = &yynewGLRStackItem (yystackp, yytrue)->yystate; @@ -1334,8 +1345,8 @@ yyglrShift (yyGLRStack* yystackp, size_t yyk, yyStateNum yylrState, yynewState->yyposn = yyposn; yynewState->yyresolved = yytrue; yynewState->yypred = yystackp->yytops.yystates[yyk]; - yynewState->yysemantics.yysval = *yyvalp; - yynewState->yyloc = *yylocp; + yynewState->yysemantics.yysval = *yyvalp;]b4_locations_if([ + yynewState->yyloc = *yylocp;])[ yystackp->yytops.yystates[yyk] = yynewState; YY_RESERVE_GLRSTACK (yystackp); @@ -1369,7 +1380,7 @@ yyglrShiftDefer (yyGLRStack* yystackp, size_t yyk, yyStateNum yylrState, * for userAction. */ static inline YYRESULTTAG yydoAction (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, - YYSTYPE* yyvalp, YYLTYPE* yylocp]b4_user_formals[) + YYSTYPE* yyvalp]b4_locuser_formals[) { int yynrhs = yyrhsLength (yyrule); @@ -1381,8 +1392,8 @@ yydoAction (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, yystackp->yynextFree -= yynrhs; yystackp->yyspaceLeft += yynrhs; yystackp->yytops.yystates[0] = & yystackp->yynextFree[-1].yystate; - return yyuserAction (yyrule, yynrhs, rhs, - yyvalp, yylocp, yystackp]b4_user_args[); + return yyuserAction (yyrule, yynrhs, rhs, yystackp, + yyvalp]b4_locuser_args[); } else { @@ -1406,7 +1417,7 @@ yydoAction (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, yyupdateSplit (yystackp, yys); yystackp->yytops.yystates[yyk] = yys; return yyuserAction (yyrule, yynrhs, yyrhsVals + YYMAXRHS + YYMAXLEFT - 1, - yyvalp, yylocp, yystackp]b4_user_args[); + yystackp, yyvalp]b4_locuser_args[); } } @@ -1425,7 +1436,7 @@ do { \ /*ARGSUSED*/ static inline void yy_reduce_print (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, - YYSTYPE* yyvalp, YYLTYPE* yylocp]b4_user_formals[) + YYSTYPE* yyvalp]b4_locuser_formals[) { int yynrhs = yyrhsLength (yyrule); yybool yynormal __attribute__ ((__unused__)) = @@ -1433,8 +1444,8 @@ yy_reduce_print (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, yyGLRStackItem* yyvsp = (yyGLRStackItem*) yystackp->yytops.yystates[yyk]; int yylow = 1; int yyi; - YYUSE (yyvalp); - YYUSE (yylocp); + YYUSE (yyvalp);]b4_locations_if([ + YYUSE (yylocp);])[ ]b4_parse_param_use[]dnl [ YYFPRINTF (stderr, "Reducing stack %lu by rule %d (line %lu):\n", (unsigned long int) yyk, yyrule - 1, @@ -1471,17 +1482,16 @@ yyglrReduce (yyGLRStack* yystackp, size_t yyk, yyRuleNum yyrule, if (yyforceEval || yystackp->yysplitPoint == YY_NULL) { - YYSTYPE yysval; - YYLTYPE yyloc; + YYSTYPE yysval;]b4_locations_if([ + YYLTYPE yyloc;])[ - YY_REDUCE_PRINT ((yystackp, yyk, yyrule, &yysval, &yyloc]b4_user_args[)); - YYCHK (yydoAction (yystackp, yyk, yyrule, &yysval, - &yyloc]b4_user_args[)); + YY_REDUCE_PRINT ((yystackp, yyk, yyrule, &yysval]b4_locuser_args([&yyloc])[)); + YYCHK (yydoAction (yystackp, yyk, yyrule, &yysval]b4_locuser_args([&yyloc])[)); YY_SYMBOL_PRINT ("-> $$ =", yyr1[yyrule], &yysval, &yyloc); yyglrShift (yystackp, yyk, yyLRgotoState (yystackp->yytops.yystates[yyk]->yylrState, yylhsNonterm (yyrule)), - yyposn, &yysval, &yyloc); + yyposn, &yysval]b4_locations_if([, &yyloc])[); } else { @@ -1699,13 +1709,13 @@ yyresolveStates (yyGLRState* yys, int yyn, * semantic values if invoked). */ static YYRESULTTAG yyresolveAction (yySemanticOption* yyopt, yyGLRStack* yystackp, - YYSTYPE* yyvalp, YYLTYPE* yylocp]b4_user_formals[) + YYSTYPE* yyvalp]b4_locuser_formals[) { yyGLRStackItem yyrhsVals[YYMAXRHS + YYMAXLEFT + 1]; int yynrhs; int yychar_current; - YYSTYPE yylval_current; - YYLTYPE yylloc_current; + YYSTYPE yylval_current;]b4_locations_if([ + YYLTYPE yylloc_current;])[ YYRESULTTAG yyflag; yynrhs = yyrhsLength (yyopt->yyrule); @@ -1723,17 +1733,17 @@ yyresolveAction (yySemanticOption* yyopt, yyGLRStack* yystackp, /* Set default location. */ yyrhsVals[YYMAXRHS + YYMAXLEFT - 1].yystate.yyloc = yyopt->yystate->yyloc;]])[ yychar_current = yychar; - yylval_current = yylval; - yylloc_current = yylloc; + yylval_current = yylval;]b4_locations_if([ + yylloc_current = yylloc;])[ yychar = yyopt->yyrawchar; - yylval = yyopt->yyval; - yylloc = yyopt->yyloc; + yylval = yyopt->yyval;]b4_locations_if([ + yylloc = yyopt->yyloc;])[ yyflag = yyuserAction (yyopt->yyrule, yynrhs, - yyrhsVals + YYMAXRHS + YYMAXLEFT - 1, - yyvalp, yylocp, yystackp]b4_user_args[); + yyrhsVals + YYMAXRHS + YYMAXLEFT - 1, + yystackp, yyvalp]b4_locuser_args[); yychar = yychar_current; - yylval = yylval_current; - yylloc = yylloc_current; + yylval = yylval_current;]b4_locations_if([ + yylloc = yylloc_current;])[ return yyflag; } @@ -1873,15 +1883,13 @@ static YYRESULTTAG yyresolveValue (yyGLRState* yys, yyGLRStack* yystackp]b4_user_formals[) { yySemanticOption* yyoptionList = yys->yysemantics.yyfirstVal; - yySemanticOption* yybest; + yySemanticOption* yybest = yyoptionList; yySemanticOption** yypp; - yybool yymerge; + yybool yymerge = yyfalse; YYSTYPE yysval; - YYRESULTTAG yyflag; - YYLTYPE *yylocp = &yys->yyloc; + YYRESULTTAG yyflag;]b4_locations_if([ + YYLTYPE *yylocp = &yys->yyloc;])[ - yybest = yyoptionList; - yymerge = yyfalse; for (yypp = &yyoptionList->yynext; *yypp != YY_NULL; ) { yySemanticOption* yyp = *yypp; @@ -1922,22 +1930,20 @@ yyresolveValue (yyGLRState* yys, yyGLRStack* yystackp]b4_user_formals[) { yySemanticOption* yyp; int yyprec = yydprec[yybest->yyrule]; - yyflag = yyresolveAction (yybest, yystackp, &yysval, - yylocp]b4_user_args[); + yyflag = yyresolveAction (yybest, yystackp, &yysval]b4_locuser_args[); if (yyflag == yyok) for (yyp = yybest->yynext; yyp != YY_NULL; yyp = yyp->yynext) { if (yyprec == yydprec[yyp->yyrule]) { - YYSTYPE yysval_other; - YYLTYPE yydummy; - yyflag = yyresolveAction (yyp, yystackp, &yysval_other, - &yydummy]b4_user_args[); + YYSTYPE yysval_other;]b4_locations_if([ + YYLTYPE yydummy;])[ + yyflag = yyresolveAction (yyp, yystackp, &yysval_other]b4_locuser_args([&yydummy])[); if (yyflag != yyok) { yydestruct ("Cleanup: discarding incompletely merged value for", yystos[yys->yylrState], - &yysval]b4_locations_if([, yylocp])[]b4_user_args[); + &yysval]b4_locuser_args[); break; } yyuserMerge (yymerger[yyp->yyrule], &yysval, &yysval_other); @@ -1945,7 +1951,7 @@ yyresolveValue (yyGLRState* yys, yyGLRStack* yystackp]b4_user_formals[) } } else - yyflag = yyresolveAction (yybest, yystackp, &yysval, yylocp]b4_user_args[); + yyflag = yyresolveAction (yybest, yystackp, &yysval]b4_locuser_args([yylocp])[); if (yyflag == yyok) { @@ -2243,7 +2249,7 @@ yyrecoverSyntaxError (yyGLRStack* yystackp]b4_user_formals[) YYLLOC_DEFAULT ((yys->yyloc), yyerror_range, 2);]])[ yytoken = YYTRANSLATE (yychar); yydestruct ("Error: discarding", - yytoken, &yylval]b4_locations_if([, &yylloc])[]b4_user_args[); + yytoken, &yylval]b4_locuser_args([&yylloc])[); } YYDPRINTF ((stderr, "Reading a token: ")); yychar = YYLEX; @@ -2293,19 +2299,20 @@ yyrecoverSyntaxError (yyGLRStack* yystackp]b4_user_formals[) if (0 <= yyj && yyj <= YYLAST && yycheck[yyj] == YYTERROR && yyisShiftAction (yytable[yyj])) { - /* Shift the error token having adjusted its location. */ - YYLTYPE yyerrloc;]b4_locations_if([[ + /* Shift the error token. */]b4_locations_if([[ + /* First adjust its location.*/ + YYLTYPE yyerrloc; yystackp->yyerror_range[2].yystate.yyloc = yylloc; YYLLOC_DEFAULT (yyerrloc, (yystackp->yyerror_range), 2);]])[ YY_SYMBOL_PRINT ("Shifting", yystos[yytable[yyj]], &yylval, &yyerrloc); yyglrShift (yystackp, 0, yytable[yyj], - yys->yyposn, &yylval, &yyerrloc); + yys->yyposn, &yylval]b4_locations_if([, &yyerrloc])[); yys = yystackp->yytops.yystates[0]; break; } - } -]b4_locations_if([[ yystackp->yyerror_range[1].yystate.yyloc = yys->yyloc;]])[ + }]b4_locations_if([[ + yystackp->yyerror_range[1].yystate.yyloc = yys->yyloc;]])[ if (yys->yypred != YY_NULL) yydestroyGLRState ("Error: popping", yys]b4_user_args[); yystackp->yytops.yystates[0] = yys->yypred; @@ -2371,7 +2378,7 @@ m4_popdef([b4_at_dollar])])dnl case 2: goto yyexhaustedlab; default: goto yybuglab; } - yyglrShift (&yystack, 0, 0, 0, &yylval, &yylloc); + yyglrShift (&yystack, 0, 0, 0, &yylval]b4_locations_if([, &yylloc])[); yyposn = 0; while (YYID (yytrue)) @@ -2429,7 +2436,7 @@ m4_popdef([b4_at_dollar])])dnl YY_SYMBOL_PRINT ("Shifting", yytoken, &yylval, &yylloc); yychar = YYEMPTY; yyposn += 1; - yyglrShift (&yystack, 0, yyaction, yyposn, &yylval, &yylloc); + yyglrShift (&yystack, 0, yyaction, yyposn, &yylval]b4_locations_if([, &yylloc])[); if (0 < yystack.yyerrState) yystack.yyerrState -= 1; } @@ -2505,7 +2512,7 @@ m4_popdef([b4_at_dollar])])dnl YYDPRINTF ((stderr, "On stack %lu, ", (unsigned long int) yys)); YY_SYMBOL_PRINT ("shifting", yytoken_to_shift, &yylval, &yylloc); yyglrShift (&yystack, yys, yyaction, yyposn, - &yylval, &yylloc); + &yylval]b4_locations_if([, &yylloc])[); YYDPRINTF ((stderr, "Stack %lu now in state #%d\n", (unsigned long int) yys, yystack.yytops.yystates[yys]->yylrState)); @@ -2545,8 +2552,7 @@ m4_popdef([b4_at_dollar])])dnl yyreturn: if (yychar != YYEMPTY) yydestruct ("Cleanup: discarding lookahead", - YYTRANSLATE (yychar), - &yylval]b4_locations_if([, &yylloc])[]b4_user_args[); + YYTRANSLATE (yychar), &yylval]b4_locuser_args([&yylloc])[); /* If the stack is well-formed, pop the stack until it is empty, destroying its entries as we go. But free the stack regardless From 2a1bd0d7fec51ea91cee0406805f608e79cb8876 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Fri, 30 Mar 2012 16:45:47 +0200 Subject: [PATCH 10/14] c++: locations: remove useless "inline". * data/location.cc: "inline" is implicit when defining methods in the class definition. --- data/location.cc | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/data/location.cc b/data/location.cc index f4fc9cc5..30f0a02f 100644 --- a/data/location.cc +++ b/data/location.cc @@ -50,7 +50,7 @@ b4_copyright([Positions for Bison parsers in C++], ])[ /// Initialization. - inline void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) + void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) { filename = fn; line = ]b4_location_initial_line[; @@ -61,14 +61,14 @@ b4_copyright([Positions for Bison parsers in C++], ** \{ */ public: /// (line related) Advance to the COUNT next lines. - inline void lines (int count = 1) + void lines (int count = 1) { column = ]b4_location_initial_column[; line += count; } /// (column related) Advance to the COUNT next columns. - inline void columns (int count = 1) + void columns (int count = 1) { column = std::max (]b4_location_initial_column[u, column + count); } @@ -176,7 +176,7 @@ b4_copyright([Locations for Bison parsers in C++], ])[ /// Initialization. - inline void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) + void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) { begin.initialize (fn); end = begin; @@ -186,19 +186,19 @@ b4_copyright([Locations for Bison parsers in C++], ** \{ */ public: /// Reset initial location to final location. - inline void step () + void step () { begin = end; } /// Extend the current location to the COUNT next columns. - inline void columns (unsigned int count = 1) + void columns (unsigned int count = 1) { end += count; } /// Extend the current location to the COUNT next lines. - inline void lines (unsigned int count = 1) + void lines (unsigned int count = 1) { end.lines (count); } From 2091988f7e4bb9020a38624601fc500631b0269b Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Tue, 23 Sep 2008 13:49:41 +0200 Subject: [PATCH 11/14] c++: locations: provide convenience constructors. * data/location.cc (position::position): Accept file, line and column as arguments with default values. Always qualify initial line and column literals as unsigned. (location::location): Provide convenience constructors. (cherry picked from commit 0634493cdde92cbdb8d9fb95a5bebe596bb53798) Conflicts: ChangeLog-2012 data/location.cc --- data/location.cc | 43 +++++++++++++++++++++++++++++++------------ 1 file changed, 31 insertions(+), 12 deletions(-) diff --git a/data/location.cc b/data/location.cc index 30f0a02f..da70d9d1 100644 --- a/data/location.cc +++ b/data/location.cc @@ -41,29 +41,32 @@ b4_copyright([Positions for Bison parsers in C++], class position { public: -]m4_ifdef([b4_location_constructors], [ +]m4_ifdef([b4_location_constructors], [[ /// Construct a position. - position () - : filename (YY_NULL), line (]b4_location_initial_line[), column (]b4_location_initial_column[) + explicit position (]b4_percent_define_get([[filename_type]])[* f = YY_NULL, + unsigned int l = ]b4_location_initial_line[u, + unsigned int c = ]b4_location_initial_column[u) + : filename (f) + , line (l) + , column (c) { } -])[ +]])[ /// Initialization. void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) { filename = fn; - line = ]b4_location_initial_line[; - column = ]b4_location_initial_column[; + line = ]b4_location_initial_line[u; + column = ]b4_location_initial_column[u; } /** \name Line and Column related manipulators ** \{ */ - public: /// (line related) Advance to the COUNT next lines. void lines (int count = 1) { - column = ]b4_location_initial_column[; + column = ]b4_location_initial_column[u; line += count; } @@ -74,7 +77,6 @@ b4_copyright([Positions for Bison parsers in C++], } /** \} */ - public: /// File name to which this position refers. ]b4_percent_define_get([[filename_type]])[* filename; /// Current line number. @@ -168,9 +170,26 @@ b4_copyright([Locations for Bison parsers in C++], { public: ]m4_ifdef([b4_location_constructors], [ - /// Construct a location. - location () - : begin (), end () + /// Construct a location from \a b to \a e. + location (const position& b, const position& e) + : begin (b) + , end (e) + { + } + + /// Construct a 0-width location in \a p. + explicit location (const position& p = position ()) + : begin (p) + , end (p) + { + } + + /// Construct a 0-width location in \a f, \a l, \a c. + explicit location (]b4_percent_define_get([[filename_type]])[* f, + unsigned int l = ]b4_location_initial_line[u, + unsigned int c = ]b4_location_initial_column[u) + : begin (f, l, c) + , end (f, l, c) { } From 936c88d178d432aecafc40c53598249249991b35 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Sat, 31 Mar 2012 09:46:12 +0200 Subject: [PATCH 12/14] doc: c++: complete the location documentation. * data/location.cc (position::initialize, location::initialize): Also accept line and column, with default values. * doc/bison.texinfo (C++ position, C++ location): New nodes. Describe more thoroughly these classes. Fix several Texinfo misuses. --- NEWS | 6 +++ data/location.cc | 14 ++++--- doc/bison.texinfo | 102 ++++++++++++++++++++++++++++++++++++---------- 3 files changed, 95 insertions(+), 27 deletions(-) diff --git a/NEWS b/NEWS index d972d85d..f552c323 100644 --- a/NEWS +++ b/NEWS @@ -34,6 +34,12 @@ Bison News C and C++ parsers use nullptr instead of 0 when __cplusplus is 201103L or higher. +** C++ locations: + + The position and location constructors (and their initialize + methods) accept new arguments for line and column. Several issues + in the documentation were fixed. + * Changes in version 2.5 (2011-05-14): ** Grammar symbol names can now contain non-initial dashes: diff --git a/data/location.cc b/data/location.cc index da70d9d1..624c3c15 100644 --- a/data/location.cc +++ b/data/location.cc @@ -54,11 +54,13 @@ b4_copyright([Positions for Bison parsers in C++], ]])[ /// Initialization. - void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) + void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL, + unsigned int l = ]b4_location_initial_line[u, + unsigned int c = ]b4_location_initial_column[u) { filename = fn; - line = ]b4_location_initial_line[u; - column = ]b4_location_initial_column[u; + line = l; + column = c; } /** \name Line and Column related manipulators @@ -195,9 +197,11 @@ b4_copyright([Locations for Bison parsers in C++], ])[ /// Initialization. - void initialize (]b4_percent_define_get([[filename_type]])[* fn = YY_NULL) + void initialize (]b4_percent_define_get([[filename_type]])[* f = YY_NULL, + unsigned int l = ]b4_location_initial_line[u, + unsigned int c = ]b4_location_initial_column[u) { - begin.initialize (fn); + begin.initialize (f, l, c); end = begin; } diff --git a/doc/bison.texinfo b/doc/bison.texinfo index 97cd9614..76a7dbae 100644 --- a/doc/bison.texinfo +++ b/doc/bison.texinfo @@ -316,6 +316,11 @@ C++ Parsers * C++ Scanner Interface:: Exchanges between yylex and parse * A Complete C++ Example:: Demonstrating their use +C++ Location Values + +* C++ position:: One point in the source file +* C++ location:: Two points in the source file + A Complete C++ Example * Calc++ --- C++ Calculator:: The specifications @@ -8882,55 +8887,98 @@ define a @code{position}, a single point in a file, and a @code{location}, a range composed of a pair of @code{position}s (possibly spanning several files). -@deftypemethod {position} {std::string*} file +@tindex uint +In this section @code{uint} is an abbreviation for @code{unsigned int}: in +genuine code only the latter is used. + +@menu +* C++ position:: One point in the source file +* C++ location:: Two points in the source file +@end menu + +@node C++ position +@subsubsection C++ @code{position} + +@deftypeop {Constructor} {position} {} position (std::string* @var{file} = 0, uint @var{line} = 1, uint @var{col} = 1) +Create a @code{position} denoting a given point. Note that @code{file} is +not reclaimed when the @code{position} is destroyed: memory managed must be +handled elsewhere. +@end deftypeop + +@deftypemethod {position} {void} initialize (std::string* @var{file} = 0, uint @var{line} = 1, uint @var{col} = 1) +Reset the position to the given values. +@end deftypemethod + +@deftypeivar {position} {std::string*} file The name of the file. It will always be handled as a pointer, the parser will never duplicate nor deallocate it. As an experimental feature you may change it to @samp{@var{type}*} using @samp{%define filename_type "@var{type}"}. -@end deftypemethod +@end deftypeivar -@deftypemethod {position} {unsigned int} line +@deftypeivar {position} {uint} line The line, starting at 1. -@end deftypemethod +@end deftypeivar -@deftypemethod {position} {unsigned int} lines (int @var{height} = 1) +@deftypemethod {position} {uint} lines (int @var{height} = 1) Advance by @var{height} lines, resetting the column number. @end deftypemethod -@deftypemethod {position} {unsigned int} column -The column, starting at 0. -@end deftypemethod +@deftypeivar {position} {uint} column +The column, starting at 1. +@end deftypeivar -@deftypemethod {position} {unsigned int} columns (int @var{width} = 1) +@deftypemethod {position} {uint} columns (int @var{width} = 1) Advance by @var{width} columns, without changing the line number. @end deftypemethod -@deftypemethod {position} {position&} operator+= (position& @var{pos}, int @var{width}) -@deftypemethodx {position} {position} operator+ (const position& @var{pos}, int @var{width}) -@deftypemethodx {position} {position&} operator-= (const position& @var{pos}, int @var{width}) -@deftypemethodx {position} {position} operator- (position& @var{pos}, int @var{width}) +@deftypemethod {position} {position&} operator+= (int @var{width}) +@deftypemethodx {position} {position} operator+ (int @var{width}) +@deftypemethodx {position} {position&} operator-= (int @var{width}) +@deftypemethodx {position} {position} operator- (int @var{width}) Various forms of syntactic sugar for @code{columns}. @end deftypemethod -@deftypemethod {position} {position} operator<< (std::ostream @var{o}, const position& @var{p}) +@deftypemethod {position} {bool} operator== (const position& @var{that}) +@deftypemethodx {position} {bool} operator!= (const position& @var{that}) +Whether @code{*this} and @code{that} denote equal/different positions. +@end deftypemethod + +@deftypefun {std::ostream&} operator<< (std::ostream& @var{o}, const position& @var{p}) Report @var{p} on @var{o} like this: @samp{@var{file}:@var{line}.@var{column}}, or @samp{@var{line}.@var{column}} if @var{file} is null. +@end deftypefun + +@node C++ location +@subsubsection C++ @code{location} + +@deftypeop {Constructor} {location} {} location (const position& @var{begin}, const position& @var{end}) +Create a @code{Location} from the endpoints of the range. +@end deftypeop + +@deftypeop {Constructor} {location} {} location (const position& @var{pos} = position()) +@deftypeopx {Constructor} {location} {} location (std::string* @var{file}, uint @var{line}, uint @var{col}) +Create a @code{Location} denoting an empty range located at a given point. +@end deftypeop + +@deftypemethod {location} {void} initialize (std::string* @var{file} = 0, uint @var{line} = 1, uint @var{col} = 1) +Reset the location to an empty range at the given values. @end deftypemethod -@deftypemethod {location} {position} begin -@deftypemethodx {location} {position} end +@deftypeivar {location} {position} begin +@deftypeivarx {location} {position} end The first, inclusive, position of the range, and the first beyond. -@end deftypemethod +@end deftypeivar -@deftypemethod {location} {unsigned int} columns (int @var{width} = 1) -@deftypemethodx {location} {unsigned int} lines (int @var{height} = 1) +@deftypemethod {location} {uint} columns (int @var{width} = 1) +@deftypemethodx {location} {uint} lines (int @var{height} = 1) Advance the @code{end} position. @end deftypemethod -@deftypemethod {location} {location} operator+ (const location& @var{begin}, const location& @var{end}) -@deftypemethodx {location} {location} operator+ (const location& @var{begin}, int @var{width}) -@deftypemethodx {location} {location} operator+= (const location& @var{loc}, int @var{width}) +@deftypemethod {location} {location} operator+ (const location& @var{end}) +@deftypemethodx {location} {location} operator+ (int @var{width}) +@deftypemethodx {location} {location} operator+= (int @var{width}) Various forms of syntactic sugar. @end deftypemethod @@ -8938,6 +8986,16 @@ Various forms of syntactic sugar. Move @code{begin} onto @code{end}. @end deftypemethod +@deftypemethod {location} {bool} operator== (const location& @var{that}) +@deftypemethodx {location} {bool} operator!= (const location& @var{that}) +Whether @code{*this} and @code{that} denote equal/different ranges of +positions. +@end deftypemethod + +@deftypefun {std::ostream&} operator<< (std::ostream& @var{o}, const location& @var{p}) +Report @var{p} on @var{o}, taking care of special cases such as: no +@code{filename} defined, or equal filename/line or column. +@end deftypefun @node C++ Parser Interface @subsection C++ Parser Interface From 059736b7b57d61d1aa3d4d414d29d0c2fe919f40 Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Sun, 1 Apr 2012 11:14:28 +0200 Subject: [PATCH 13/14] build: remove ancient Autoconf tests. lib/subpipe.c was removed in 47fa574761319b0a422691223c9b8a9a72f36aa2. * m4/subpipe.m4: Remove. * configure.ac (BISON_PREREQ_SUBPIPE): Remove. --- configure.ac | 1 - m4/subpipe.m4 | 28 ---------------------------- 2 files changed, 29 deletions(-) delete mode 100644 m4/subpipe.m4 diff --git a/configure.ac b/configure.ac index 210002b2..688e18ef 100644 --- a/configure.ac +++ b/configure.ac @@ -137,7 +137,6 @@ gl_INIT # Checks for library functions. AC_CHECK_FUNCS_ONCE([setlocale]) AM_WITH_DMALLOC -BISON_PREREQ_SUBPIPE BISON_PREREQ_TIMEVAR # Gettext. diff --git a/m4/subpipe.m4 b/m4/subpipe.m4 deleted file mode 100644 index 0079c045..00000000 --- a/m4/subpipe.m4 +++ /dev/null @@ -1,28 +0,0 @@ -# -*- Autoconf -*- -# Checks required to run `subpipe'. -# -# Copyright (C) 2002-2003, 2005, 2009-2012 Free Software Foundation, -# Inc. -# -# This program is free software: you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see . - -# Written by Paul Eggert . - -AC_DEFUN([BISON_PREREQ_SUBPIPE], -[ - AC_TYPE_PID_T - AC_HEADER_SYS_WAIT - AC_CHECK_FUNCS(dup2 waitpid) - AC_FUNC_FORK -]) From 681dda24bab97297d43a09fb50f95110b790c3ce Mon Sep 17 00:00:00 2001 From: Akim Demaille Date: Sun, 1 Apr 2012 12:15:19 +0200 Subject: [PATCH 14/14] bump to 2012 in skeletons. * data/glr.c, data/glr.cc, data/lalr1.cc, data/lalr1.java, * data/location.cc, data/yacc.c: Bump copyright year ranges. --- data/glr.c | 4 ++-- data/glr.cc | 2 +- data/lalr1.cc | 6 +++--- data/lalr1.java | 2 +- data/location.cc | 2 +- data/yacc.c | 4 ++-- 6 files changed, 10 insertions(+), 10 deletions(-) diff --git a/data/glr.c b/data/glr.c index 65107d9a..d0b26926 100644 --- a/data/glr.c +++ b/data/glr.c @@ -164,7 +164,7 @@ m4_changecom() m4_divert_push(0)dnl @output(b4_parser_file_name@)@ b4_copyright([Skeleton implementation for Bison GLR parsers in C], - [2002-2011]) + [2002-2012]) [ /* C GLR parser skeleton written by Paul Hilfinger. */ @@ -2671,7 +2671,7 @@ m4_if(b4_skeleton, ["glr.c"], [b4_defines_if( [@output(b4_spec_defines_file@)@ b4_copyright([Skeleton interface for Bison GLR parsers in C], - [2002-2011]) + [2002-2012]) b4_shared_declarations diff --git a/data/glr.cc b/data/glr.cc index f6b24474..0f9141c4 100644 --- a/data/glr.cc +++ b/data/glr.cc @@ -220,7 +220,7 @@ m4_popdef([b4_parse_param]) m4_divert_push(0) @output(b4_spec_defines_file@)@ b4_copyright([Skeleton interface for Bison GLR parsers in C++], - [2002-2006, 2009-2011])[ + [2002-2006, 2009-2012])[ /* C++ GLR parser skeleton written by Akim Demaille. */ diff --git a/data/lalr1.cc b/data/lalr1.cc index dc0cc8cc..d7201dd4 100644 --- a/data/lalr1.cc +++ b/data/lalr1.cc @@ -35,7 +35,7 @@ m4_divert_push(0)dnl b4_defines_if( [@output(b4_spec_defines_file@)@ b4_copyright([Skeleton interface for Bison LALR(1) parsers in C++], - [2002-2011]) + [2002-2012]) dnl FIXME: This is wrong, we want computed header guards. [ /* C++ LALR(1) parser skeleton written by Akim Demaille. */ @@ -284,7 +284,7 @@ b4_percent_code_get([[provides]])[]dnl ])dnl @output(b4_parser_file_name@)@ b4_copyright([Skeleton implementation for Bison LALR(1) parsers in C++], - [2002-2011]) + [2002-2012]) b4_percent_code_get([[top]])[]dnl m4_if(b4_prefix, [yy], [], [ @@ -1141,7 +1141,7 @@ b4_error_verbose_if([int yystate, int yytoken], dnl @output(b4_dir_prefix[]stack.hh@)@ b4_copyright([Stack handling for Bison parsers in C++], - [2002-2011])[ + [2002-2012])[ #ifndef BISON_STACK_HH # define BISON_STACK_HH diff --git a/data/lalr1.java b/data/lalr1.java index b5884c40..103c03dd 100644 --- a/data/lalr1.java +++ b/data/lalr1.java @@ -25,7 +25,7 @@ m4_ifval(m4_defn([b4_symbol_destructors]), m4_divert_push(0)dnl @output(b4_parser_file_name@)@ b4_copyright([Skeleton implementation for Bison LALR(1) parsers in Java], - [2007-2011]) + [2007-2012]) b4_percent_define_ifdef([package], [package b4_percent_define_get([package]); ])[/* First part of user declarations. */ diff --git a/data/location.cc b/data/location.cc index 624c3c15..cb0f1f91 100644 --- a/data/location.cc +++ b/data/location.cc @@ -151,7 +151,7 @@ b4_copyright([Positions for Bison parsers in C++], #endif // not BISON_POSITION_HH] @output(b4_dir_prefix[]location.hh@)@ b4_copyright([Locations for Bison parsers in C++], - [2002-2007, 2009-2011])[ + [2002-2007, 2009-2012])[ /** ** \file location.hh diff --git a/data/yacc.c b/data/yacc.c index 8d26479d..284e13de 100644 --- a/data/yacc.c +++ b/data/yacc.c @@ -234,7 +234,7 @@ m4_changecom() m4_divert_push(0)dnl @output(b4_parser_file_name@)@ b4_copyright([Bison implementation for Yacc-like parsers in C], - [1984, 1989-1990, 2000-2011])[ + [1984, 1989-1990, 2000-2012])[ /* C LALR(1) parser skeleton written by Richard Stallman, by simplifying the original so-called "semantic" parser. */ @@ -2072,7 +2072,7 @@ yypushreturn:]])[ b4_defines_if( [@output(b4_spec_defines_file@)@ b4_copyright([Bison interface for Yacc-like parsers in C], - [1984, 1989-1990, 2000-2011]) + [1984, 1989-1990, 2000-2012]) b4_percent_code_get([[requires]])[]dnl