Re: Improving the notation for ecpg.addons rules - Mailing list pgsql-hackers

From Tom Lane
Subject Re: Improving the notation for ecpg.addons rules
Date
Msg-id 1625779.1724178803@sss.pgh.pa.us
Whole thread Raw
In response to Re: Improving the notation for ecpg.addons rules  (Tom Lane <tgl@sss.pgh.pa.us>)
List pgsql-hackers
I wrote:
> Michael Paquier <michael@paquier.xyz> writes:
>> It looks like %replace_line expects all its elements to have one space
>> between each token, still this is not enforced with a check across its
>> hardcoded elements?

> Yeah, I was wondering about that.  I wouldn't do it exactly like
> that, but with a check that the entry gets matched somewhere.

Here's a patch for that (again based on the other patch series).
This did not turn up anything interesting, but it's probably
worth keeping.

            regards, tom lane

diff --git a/src/interfaces/ecpg/preproc/parse.pl b/src/interfaces/ecpg/preproc/parse.pl
index 98d44d4bf2..998822ce73 100644
--- a/src/interfaces/ecpg/preproc/parse.pl
+++ b/src/interfaces/ecpg/preproc/parse.pl
@@ -33,7 +33,9 @@ GetOptions(


 # These hash tables define additional transformations to apply to
-# grammar rules.
+# grammar rules.  For bug-detection purposes, we count usages of
+# each hash table entry in a second hash table, and verify that
+# all the entries get used.

 # Substitutions to apply to tokens whenever they are seen in a rule.
 my %replace_token = (
@@ -44,6 +46,8 @@ my %replace_token = (
     'IDENT' => 'ecpg_ident',
     'PARAM' => 'ecpg_param',);

+my %replace_token_used;
+
 # This hash can provide a result type to override "void" for nonterminals
 # that need that, or it can specify 'ignore' to cause us to skip the rule
 # for that nonterminal.  (In either case, ecpg.trailer had better provide
@@ -68,6 +72,8 @@ my %replace_types = (
     'plassign_target' => 'ignore',
     'plassign_equals' => 'ignore',);

+my %replace_types_used;
+
 # This hash provides an "ignore" option or substitute expansion for any
 # rule or rule alternative.  The hash key is the same "concattokens" tag
 # used for lookup in ecpg.addons.
@@ -111,6 +117,8 @@ my %replace_line = (
       'PREPARE prepared_name prep_type_clause AS PreparableStmt',
     'var_nameColId' => 'ECPGColId');

+my %replace_line_used;
+

 # Declare assorted state variables.

@@ -198,6 +206,30 @@ foreach (keys %addons)
     die "addon rule $_ was matched multiple times\n" if $addons{$_}{used} > 1;
 }

+# Likewise cross-check that entries in our internal hash tables match something.
+foreach (keys %replace_token)
+{
+    die "replace_token entry $_ was never used\n"
+      if !defined($replace_token_used{$_});
+    # multiple use of a replace_token entry is fine
+}
+
+foreach (keys %replace_types)
+{
+    die "replace_types entry $_ was never used\n"
+      if !defined($replace_types_used{$_});
+    die "replace_types entry $_ was matched multiple times\n"
+      if $replace_types_used{$_} > 1;
+}
+
+foreach (keys %replace_line)
+{
+    die "replace_line entry $_ was never used\n"
+      if !defined($replace_line_used{$_});
+    die "replace_line entry $_ was matched multiple times\n"
+      if $replace_line_used{$_} > 1;
+}
+

 # Read the backend grammar.
 sub main
@@ -400,6 +432,7 @@ sub main
             # Apply replace_token substitution if we have one.
             if (exists $replace_token{ $arr[$fieldIndexer] })
             {
+                $replace_token_used{ $arr[$fieldIndexer] }++;
                 $arr[$fieldIndexer] = $replace_token{ $arr[$fieldIndexer] };
             }

@@ -425,6 +458,7 @@ sub main
                     && $replace_types{$non_term_id} eq 'ignore')
                 {
                     # We'll ignore this nonterminal and rule altogether.
+                    $replace_types_used{$non_term_id}++;
                     $copymode = 0;
                     next line;
                 }
@@ -451,6 +485,7 @@ sub main
                       . $replace_types{$non_term_id} . ' '
                       . $non_term_id;
                     add_to_buffer('types', $tstr);
+                    $replace_types_used{$non_term_id}++;
                 }

                 # Emit the target part of the rule.
@@ -616,8 +651,10 @@ sub emit_rule

     # apply replace_line substitution if any
     my $rep = $replace_line{$tag};
-    if ($rep)
+    if (defined $rep)
     {
+        $replace_line_used{$tag}++;
+
         if ($rep eq 'ignore')
         {
             return 0;

pgsql-hackers by date:

Previous
From: "David G. Johnston"
Date:
Subject: Re: Add new protocol message to change GUCs for usage with future protocol-only GUCs
Next
From: Alvaro Herrera
Date:
Subject: Re: MultiXact\SLRU buffers configuration