mirror of
https://git.postgresql.org/git/postgresql.git
synced 2025-01-30 19:00:29 +08:00
From: Michael Meskes <meskes@topsystem.de>
Here's the ecpg patch for the local variables bug I reported earlier:
This commit is contained in:
parent
7d55b1c7f0
commit
33c2da9725
@ -44,8 +44,5 @@ could be realised in a script.
|
||||
|
||||
Now comes my list (MM):
|
||||
|
||||
Ecpg should remove variables from its list as soon as they are undefined and
|
||||
not rely on cc to report an error.
|
||||
|
||||
Variable definitions containing static/volatile have to be possible.
|
||||
|
||||
|
@ -356,7 +356,7 @@ you are not interested in how it really works, skip this chapter.
|
||||
@comment node-name, next, previous, up
|
||||
@section To do list
|
||||
|
||||
In the alpha version the preprocessor has a lot of flaws:
|
||||
This version the preprocessor has some flaws:
|
||||
@table @asis
|
||||
|
||||
@item Preprocessor output
|
||||
|
@ -3,7 +3,7 @@
|
||||
#include "type.h"
|
||||
#include "y.tab.h"
|
||||
|
||||
extern int debugging;
|
||||
#include "extern.h"
|
||||
|
||||
#define dbg(arg) if (debugging) fprintf(stderr, "DEBUG, %d: %s\n", yylineno, #arg);
|
||||
%}
|
||||
@ -56,7 +56,7 @@ int { dbg(S_INT); return S_INT; }
|
||||
char { dbg(S_CHAR); return S_CHAR; }
|
||||
float { dbg(S_FLOAT); return S_FLOAT; }
|
||||
double { dbg(S_DOUBLE); return S_DOUBLE; }
|
||||
bool { dbg(S_BOOL); return S_BOOL; }
|
||||
bool { dbg(S_BOOL); return S_BOOL; }
|
||||
|
||||
{string} { dbg(SQL_STRING); return SQL_STRING; }
|
||||
<SQL>{ws} ;
|
||||
@ -97,6 +97,8 @@ bool { dbg(S_BOOL); return S_BOOL; }
|
||||
"]" { dbg(]); return ']'; }
|
||||
";" { dbg(;); return ';'; }
|
||||
"," { dbg(komma); return ','; }
|
||||
\{ { dbg(blockstart); return '{'; }
|
||||
\} { dbg(blockend); return'}'; }
|
||||
|
||||
<SQL>":" { dbg(:); return ':'; }
|
||||
|
||||
@ -106,6 +108,7 @@ bool { dbg(S_BOOL); return S_BOOL; }
|
||||
void
|
||||
lex_init(void)
|
||||
{
|
||||
braces_open = 0;
|
||||
BEGIN C;
|
||||
}
|
||||
|
||||
|
@ -29,27 +29,24 @@ output_line_number()
|
||||
/*
|
||||
* Handling of the variables.
|
||||
*/
|
||||
/* Since we don't want to keep track of where the functions end we just
|
||||
* have a list of functions that we search in, most reasently defined
|
||||
* function. This won't work if we use block scope for variables with the
|
||||
* same name but different types but in all other cases the c-compiler will
|
||||
* signal an error (hopefully).
|
||||
*
|
||||
* This list is leaked on program exit. This is because I don't think it is
|
||||
* important enough to spend the extra ten minutes to write the function that
|
||||
* deletes it. It would be another thing if I would have written in C++.
|
||||
|
||||
/*
|
||||
* brace level counter
|
||||
*/
|
||||
int braces_open;
|
||||
|
||||
/* This is a linked list of the variable names and types. */
|
||||
struct variable
|
||||
{
|
||||
char * name;
|
||||
struct ECPGtype * type;
|
||||
int brace_level;
|
||||
struct variable * next;
|
||||
};
|
||||
|
||||
static struct variable * allvariables = NULL;
|
||||
|
||||
struct variable *
|
||||
static struct variable *
|
||||
find_variable(char * name)
|
||||
{
|
||||
struct variable * p;
|
||||
@ -71,18 +68,42 @@ find_variable(char * name)
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
static void
|
||||
new_variable(const char * name, struct ECPGtype * type)
|
||||
{
|
||||
struct variable * p = (struct variable*) malloc(sizeof(struct variable));
|
||||
|
||||
p->name = strdup(name);
|
||||
p->type = type;
|
||||
p->brace_level = braces_open;
|
||||
|
||||
p->next = allvariables;
|
||||
allvariables = p;
|
||||
}
|
||||
|
||||
static void
|
||||
remove_variables(int brace_level)
|
||||
{
|
||||
struct variable * p, *prev;
|
||||
|
||||
for (p = prev = allvariables; p; p = p->next)
|
||||
{
|
||||
if (p->brace_level >= brace_level)
|
||||
{
|
||||
/* remove it */
|
||||
if (p == allvariables)
|
||||
prev = allvariables = p->next;
|
||||
else
|
||||
prev->next = p->next;
|
||||
|
||||
free(p);
|
||||
p = prev;
|
||||
}
|
||||
else
|
||||
prev = p;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Here are the variables that need to be handled on every request.
|
||||
@ -161,7 +182,7 @@ dump_variables(struct arguments * list)
|
||||
%token <tagname> S_EXTERN S_STATIC
|
||||
%token <tagname> S_UNSIGNED S_SIGNED
|
||||
%token <tagname> S_LONG S_SHORT S_INT S_CHAR S_FLOAT S_DOUBLE S_BOOL
|
||||
%token <tagname> '[' ']' ';' ','
|
||||
%token <tagname> '[' ']' ';' ',' '{' '}'
|
||||
|
||||
%type <type> type type_detailed varchar_type simple_type array_type
|
||||
%type <symbolname> symbol
|
||||
@ -184,7 +205,9 @@ statement : sqldeclaration
|
||||
| sqlcommit
|
||||
| sqlrollback
|
||||
| sqlstatement
|
||||
| cthing;
|
||||
| cthing
|
||||
| blockstart
|
||||
| blockend;
|
||||
|
||||
sqldeclaration : sql_startdeclare
|
||||
variable_declarations
|
||||
@ -356,6 +379,15 @@ both_anything : S_LENGTH | S_VARCHAR | S_VARCHAR2
|
||||
| '[' | ']' | ','
|
||||
| S_ANYTHING;
|
||||
|
||||
blockstart : '{' {
|
||||
braces_open++;
|
||||
fwrite(yytext, yyleng, 1, yyout);
|
||||
}
|
||||
|
||||
blockend : '}' {
|
||||
remove_variables(braces_open--);
|
||||
fwrite(yytext, yyleng, 1, yyout);
|
||||
}
|
||||
%%
|
||||
static void yyerror(char * error)
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user