Commit 35478b80 authored by Marc G. Fournier's avatar Marc G. Fournier

From: Michael Meskes <meskes@online-club.de>

+
+ Fri Aug 14 12:44:21 CEST 1998
+
+       - Added EXEC SQL DEFINE statement
+       - Set version to 2.4.0
+
+ Tue Aug 18 09:24:15 CEST 1998
+
+       - Removed keyword IS from DEFINE statement
+       - Added latest changes from gram.y
+       - Removed duplicate symbols from preproc.y
+       - Initialize sqlca structure
+       - Added check for connection to ecpglib
+       - Set version to 2.4.1
+
+ Thu Aug 20 15:31:29 CEST 1998
+
+       - Cleaned up memory allocation in ecpglib.c
+       - Set library version to 2.6
+
parent 32cfc4aa
...@@ -4,7 +4,7 @@ include $(SRCDIR)/Makefile.global ...@@ -4,7 +4,7 @@ include $(SRCDIR)/Makefile.global
PQ_INCLUDE=-I$(SRCDIR)/interfaces/libpq PQ_INCLUDE=-I$(SRCDIR)/interfaces/libpq
SO_MAJOR_VERSION=2 SO_MAJOR_VERSION=2
SO_MINOR_VERSION=5 SO_MINOR_VERSION=6
PORTNAME=@PORTNAME@ PORTNAME=@PORTNAME@
......
...@@ -24,7 +24,32 @@ ...@@ -24,7 +24,32 @@
#include <ecpglib.h> #include <ecpglib.h>
#include <sqlca.h> #include <sqlca.h>
extern int no_auto_trans; /* variables visible to the programs */
int no_auto_trans;
static struct sqlca sqlca_init =
{
{'S', 'Q', 'L', 'C', 'A', ' ', ' ', ' '},
sizeof(struct sqlca),
0,
{ 0, {0}},
{'N', 'O', 'T', ' ', 'S', 'E', 'T', ' '},
{0, 0, 0, 0, 0, 0},
{0, 0, 0, 0, 0, 0, 0, 0},
{0, 0, 0, 0, 0, 0, 0, 0}
};
struct sqlca sqlca =
{
{'S', 'Q', 'L', 'C', 'A', ' ', ' ', ' '},
sizeof(struct sqlca),
0,
{ 0, {0}},
{'N', 'O', 'T', ' ', 'S', 'E', 'T', ' '},
{0, 0, 0, 0, 0, 0},
{0, 0, 0, 0, 0, 0, 0, 0},
{0, 0, 0, 0, 0, 0, 0, 0}
};
static struct connection static struct connection
{ {
...@@ -72,39 +97,6 @@ register_error(long code, char *fmt,...) ...@@ -72,39 +97,6 @@ register_error(long code, char *fmt,...)
sqlca.sqlerrm.sqlerrml = strlen(sqlca.sqlerrm.sqlerrmc); sqlca.sqlerrm.sqlerrml = strlen(sqlca.sqlerrm.sqlerrmc);
} }
/* This function returns a newly malloced string that has the ' and \
in the argument quoted with \.
*/
static
char *
quote_postgres(char *arg)
{
char *res = (char *) malloc(2 * strlen(arg) + 1);
int i,
ri;
if (!res)
return(res);
for (i = 0, ri = 0; arg[i]; i++, ri++)
{
switch (arg[i])
{
case '\'':
case '\\':
res[ri++] = '\\';
default:
;
}
res[ri] = arg[i];
}
res[ri] = '\0';
return res;
}
static void static void
ECPGfinish(struct connection *act) ECPGfinish(struct connection *act)
{ {
...@@ -139,6 +131,54 @@ ECPGfinish(struct connection *act) ...@@ -139,6 +131,54 @@ ECPGfinish(struct connection *act)
ECPGlog("ECPGfinish: called an extra time.\n"); ECPGlog("ECPGfinish: called an extra time.\n");
} }
static char *ecpg_alloc(long size, int lineno)
{
char *new = (char *) malloc(size);
if (!new)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", lineno);
return NULL;
}
memset(new, '\0', size);
return(new);
}
/* This function returns a newly malloced string that has the ' and \
in the argument quoted with \.
*/
static
char *
quote_postgres(char *arg, int lineno)
{
char *res = (char *) ecpg_alloc(2 * strlen(arg) + 1, lineno);
int i,
ri;
if (!res)
return(res);
for (i = 0, ri = 0; arg[i]; i++, ri++)
{
switch (arg[i])
{
case '\'':
case '\\':
res[ri++] = '\\';
default:
;
}
res[ri] = arg[i];
}
res[ri] = '\0';
return res;
}
/* create a list of variables */ /* create a list of variables */
static bool static bool
create_statement(int lineno, struct statement **stmt, char *query, va_list ap) create_statement(int lineno, struct statement **stmt, char *query, va_list ap)
...@@ -146,15 +186,8 @@ create_statement(int lineno, struct statement **stmt, char *query, va_list ap) ...@@ -146,15 +186,8 @@ create_statement(int lineno, struct statement **stmt, char *query, va_list ap)
struct variable **list = &((*stmt)->inlist); struct variable **list = &((*stmt)->inlist);
enum ECPGttype type; enum ECPGttype type;
*stmt = calloc(sizeof(struct statement), 1); if (!(*stmt = (struct statement *) ecpg_alloc(sizeof(struct statement), lineno)))
if (!*stmt)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", lineno);
return false; return false;
}
(*stmt)->command = query; (*stmt)->command = query;
(*stmt)->lineno = lineno; (*stmt)->lineno = lineno;
...@@ -173,14 +206,8 @@ create_statement(int lineno, struct statement **stmt, char *query, va_list ap) ...@@ -173,14 +206,8 @@ create_statement(int lineno, struct statement **stmt, char *query, va_list ap)
{ {
struct variable *var, *ptr; struct variable *var, *ptr;
var = malloc(sizeof(struct variable)); if (!(var = (struct variable *) ecpg_alloc(sizeof(struct variable), lineno)))
if (!var)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", lineno);
return false; return false;
}
var->type = type; var->type = type;
var->value = va_arg(ap, void *); var->value = va_arg(ap, void *);
...@@ -217,7 +244,7 @@ ECPGexecute(struct statement *stmt) ...@@ -217,7 +244,7 @@ ECPGexecute(struct statement *stmt)
PGnotify *notify; PGnotify *notify;
struct variable *var; struct variable *var;
memset((char *) &sqlca, 0, sizeof (sqlca)); memcpy((char *)&sqlca, (char *)&sqlca_init, sizeof(sqlca));
copiedquery = strdup(stmt->command); copiedquery = strdup(stmt->command);
...@@ -314,36 +341,19 @@ ECPGexecute(struct statement *stmt) ...@@ -314,36 +341,19 @@ ECPGexecute(struct statement *stmt)
int slen = (var->varcharsize == 0) ? strlen((char *) var->value) : var->varcharsize; int slen = (var->varcharsize == 0) ? strlen((char *) var->value) : var->varcharsize;
char * tmp; char * tmp;
newcopy = (char *) malloc(slen + 1); if (!(newcopy = ecpg_alloc(slen + 1, stmt->lineno)))
if (!newcopy)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", stmt->lineno);
return false; return false;
}
strncpy(newcopy, (char *) var->value, slen); strncpy(newcopy, (char *) var->value, slen);
newcopy[slen] = '\0'; newcopy[slen] = '\0';
mallocedval = (char *) malloc(2 * strlen(newcopy) + 3); if (!(mallocedval = (char *) ecpg_alloc(2 * strlen(newcopy) + 3, stmt->lineno)))
if (!mallocedval)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", stmt->lineno);
return false; return false;
}
strcpy(mallocedval, "'"); strcpy(mallocedval, "'");
tmp = quote_postgres(newcopy); tmp = quote_postgres(newcopy, stmt->lineno);
if (!tmp) if (!tmp)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", stmt->lineno);
return false; return false;
}
strcat(mallocedval, tmp); strcat(mallocedval, tmp);
strcat(mallocedval, "'"); strcat(mallocedval, "'");
...@@ -360,36 +370,19 @@ ECPGexecute(struct statement *stmt) ...@@ -360,36 +370,19 @@ ECPGexecute(struct statement *stmt)
(struct ECPGgeneric_varchar *) (var->value); (struct ECPGgeneric_varchar *) (var->value);
char *tmp; char *tmp;
newcopy = (char *) malloc(variable->len + 1); if (!(newcopy = (char *) ecpg_alloc(variable->len + 1, stmt->lineno)))
if (!newcopy)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", stmt->lineno);
return false; return false;
}
strncpy(newcopy, variable->arr, variable->len); strncpy(newcopy, variable->arr, variable->len);
newcopy[variable->len] = '\0'; newcopy[variable->len] = '\0';
mallocedval = (char *) malloc(2 * strlen(newcopy) + 3); if (!(mallocedval = (char *) ecpg_alloc(2 * strlen(newcopy) + 3, stmt->lineno)))
if (!mallocedval)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", stmt->lineno);
return false; return false;
}
strcpy(mallocedval, "'"); strcpy(mallocedval, "'");
tmp = quote_postgres(newcopy); tmp = quote_postgres(newcopy, stmt->lineno);
if (!tmp) if (!tmp)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", stmt->lineno);
return false; return false;
}
strcat(mallocedval, tmp); strcat(mallocedval, tmp);
strcat(mallocedval, "'"); strcat(mallocedval, "'");
...@@ -415,16 +408,8 @@ ECPGexecute(struct statement *stmt) ...@@ -415,16 +408,8 @@ ECPGexecute(struct statement *stmt)
* Now tobeinserted points to an area that is to be inserted at * Now tobeinserted points to an area that is to be inserted at
* the first %s * the first %s
*/ */
newcopy = (char *) malloc(strlen(copiedquery) if (!(newcopy = (char *) ecpg_alloc(strlen(copiedquery) + strlen(tobeinserted) + 1, stmt->lineno)))
+ strlen(tobeinserted)
+ 1);
if (!newcopy)
{
ECPGfinish(actual_connection);
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", stmt->lineno);
return false; return false;
}
strcpy(newcopy, copiedquery); strcpy(newcopy, copiedquery);
if ((p = strstr(newcopy, ";;")) == NULL) if ((p = strstr(newcopy, ";;")) == NULL)
...@@ -858,6 +843,14 @@ ECPGdo(int lineno, char *query, ...) ...@@ -858,6 +843,14 @@ ECPGdo(int lineno, char *query, ...)
return(false); return(false);
va_end(args); va_end(args);
/* are we connected? */
if (actual_connection == NULL || actual_connection->connection == NULL)
{
ECPGlog("ECPGdo: not connected\n");
register_error(ECPG_NOT_CONN, "Not connected in line %d", lineno);
return false;
}
return(ECPGexecute(stmt)); return(ECPGexecute(stmt));
} }
...@@ -902,14 +895,10 @@ ECPGsetconn(int lineno, const char *connection_name) ...@@ -902,14 +895,10 @@ ECPGsetconn(int lineno, const char *connection_name)
bool bool
ECPGconnect(int lineno, const char *dbname, const char *user, const char *passwd, const char * connection_name) ECPGconnect(int lineno, const char *dbname, const char *user, const char *passwd, const char * connection_name)
{ {
struct connection *this = malloc(sizeof(struct connection)); struct connection *this = (struct connection *) ecpg_alloc(sizeof(struct connection), lineno);
if (!this) if (!this)
{
ECPGlog("out of memory\n");
register_error(ECPG_OUT_OF_MEMORY, "out of memory in line %d", lineno);
return false; return false;
}
if (dbname == NULL && connection_name == NULL) if (dbname == NULL && connection_name == NULL)
connection_name = "DEFAULT"; connection_name = "DEFAULT";
...@@ -937,7 +926,6 @@ ECPGconnect(int lineno, const char *dbname, const char *user, const char *passwd ...@@ -937,7 +926,6 @@ ECPGconnect(int lineno, const char *dbname, const char *user, const char *passwd
{ {
ECPGfinish(this); ECPGfinish(this);
ECPGlog("connect: could not open database %s %s%s in line %d\n", dbname ? dbname : "NULL", user ? "for user ": "", user ? user : "", lineno); ECPGlog("connect: could not open database %s %s%s in line %d\n", dbname ? dbname : "NULL", user ? "for user ": "", user ? user : "", lineno);
register_error(ECPG_CONNECT, "connect: could not open database %s.", dbname ? dbname : "NULL"); register_error(ECPG_CONNECT, "connect: could not open database %s.", dbname ? dbname : "NULL");
return false; return false;
} }
......
...@@ -2,8 +2,8 @@ SRCDIR= ../../.. ...@@ -2,8 +2,8 @@ SRCDIR= ../../..
include $(SRCDIR)/Makefile.global include $(SRCDIR)/Makefile.global
MAJOR_VERSION=2 MAJOR_VERSION=2
MINOR_VERSION=3 MINOR_VERSION=4
PATCHLEVEL=5 PATCHLEVEL=1
CFLAGS+=-I../include -DMAJOR_VERSION=$(MAJOR_VERSION) \ CFLAGS+=-I../include -DMAJOR_VERSION=$(MAJOR_VERSION) \
-DMINOR_VERSION=$(MINOR_VERSION) -DPATCHLEVEL=$(PATCHLEVEL) \ -DMINOR_VERSION=$(MINOR_VERSION) -DPATCHLEVEL=$(PATCHLEVEL) \
......
...@@ -22,7 +22,7 @@ extern char *optarg; ...@@ -22,7 +22,7 @@ extern char *optarg;
#include "extern.h" #include "extern.h"
struct _include_path *include_paths; struct _include_path *include_paths;
static int no_auto_trans = 0; int no_auto_trans = 0;
struct cursor *cur = NULL; struct cursor *cur = NULL;
static void static void
...@@ -138,10 +138,12 @@ main(int argc, char *const argv[]) ...@@ -138,10 +138,12 @@ main(int argc, char *const argv[])
else else
{ {
struct cursor *ptr; struct cursor *ptr;
struct _defines *defptr;
/* remove old cursor definitions if any are still there */ /* remove old cursor definitions if any are still there */
for (ptr = cur; ptr != NULL; ptr=ptr->next) for (ptr = cur; ptr != NULL;)
{ {
struct cursor *this = ptr;
struct arguments *l1, *l2; struct arguments *l1, *l2;
free(ptr->command); free(ptr->command);
...@@ -156,12 +158,25 @@ main(int argc, char *const argv[]) ...@@ -156,12 +158,25 @@ main(int argc, char *const argv[])
l2 = l1->next; l2 = l1->next;
free(l1); free(l1);
} }
ptr = ptr->next;
free(this);
} }
/* remove old defines as well */
for (defptr = defines; defptr != NULL;)
{
struct _defines *this = defptr;
free(defptr->new);
free(defptr->old);
defptr = defptr->next;
free(this);
}
/* initialize lex */ /* initialize lex */
lex_init(); lex_init();
/* we need two includes and a constant */ /* we need two includes and a constant */
fprintf(yyout, "/* Processed by ecpg (%d.%d.%d) */\n/*These two include files are added by the preprocessor */\n#include <ecpgtype.h>\n#include <ecpglib.h>\n\nconst int no_auto_trans = %d;\n\n", MAJOR_VERSION, MINOR_VERSION, PATCHLEVEL, no_auto_trans); fprintf(yyout, "/* Processed by ecpg (%d.%d.%d) */\n/* These two include files are added by the preprocessor */\n#include <ecpgtype.h>\n#include <ecpglib.h>\n\n", MAJOR_VERSION, MINOR_VERSION, PATCHLEVEL);
/* and parse the source */ /* and parse the source */
yyparse(); yyparse();
......
...@@ -3,7 +3,7 @@ ...@@ -3,7 +3,7 @@
/* variables */ /* variables */
extern int braces_open; extern int braces_open, no_auto_trans;
extern char *yytext; extern char *yytext;
extern int yylineno, extern int yylineno,
yyleng; yyleng;
...@@ -25,6 +25,13 @@ struct cursor { char *name; ...@@ -25,6 +25,13 @@ struct cursor { char *name;
extern struct cursor *cur; extern struct cursor *cur;
struct _defines { char *old;
char *new;
struct _defines *next;
};
extern struct _defines *defines;
/* This is a linked list of the variable names and types. */ /* This is a linked list of the variable names and types. */
struct variable struct variable
{ {
......
...@@ -46,9 +46,12 @@ struct _yy_buffer { YY_BUFFER_STATE buffer; ...@@ -46,9 +46,12 @@ struct _yy_buffer { YY_BUFFER_STATE buffer;
struct _yy_buffer * next; struct _yy_buffer * next;
} *yy_buffer = NULL; } *yy_buffer = NULL;
struct _defines *defines = NULL;
static char *old;
%} %}
%option yylineno %option yylineno
%s C SQL incl %s C SQL incl def def_ident
/* OK, here is a short description of lex/flex rules behavior. /* OK, here is a short description of lex/flex rules behavior.
* The longest pattern which matches an input string is always chosen. * The longest pattern which matches an input string is always chosen.
* For equal-length patterns, the first occurring in the rules list is chosen. * For equal-length patterns, the first occurring in the rules list is chosen.
...@@ -156,6 +159,7 @@ other . ...@@ -156,6 +159,7 @@ other .
/* some stuff needed for ecpg */ /* some stuff needed for ecpg */
ccomment "//".*\n ccomment "//".*\n
exec [eE][xX][eE][cC] exec [eE][xX][eE][cC]
define [dD][eE][fF][iI][nN][eE]
include [iI][nN][cC][lL][uU][dD][eE] include [iI][nN][cC][lL][uU][dD][eE]
sql [sS][qQ][lL] sql [sS][qQ][lL]
...@@ -307,7 +311,6 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -307,7 +311,6 @@ cppline {space}*#.*(\\{space}*\n)*\n*
<SQL>{typecast} { return TYPECAST; } <SQL>{typecast} { return TYPECAST; }
<SQL>{self}/{space}*-[\.0-9] { <SQL>{self}/{space}*-[\.0-9] {
BEGIN(xm); BEGIN(xm);
return (yytext[0]); return (yytext[0]);
...@@ -328,7 +331,6 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -328,7 +331,6 @@ cppline {space}*#.*(\\{space}*\n)*\n*
yylval.ival = atoi((char*)&yytext[1]); yylval.ival = atoi((char*)&yytext[1]);
return (PARAM); return (PARAM);
} }
<SQL>{identifier}/{space}*-{number} { <SQL>{identifier}/{space}*-{number} {
int i; int i;
ScanKeyword *keyword; ScanKeyword *keyword;
...@@ -349,13 +351,37 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -349,13 +351,37 @@ cppline {space}*#.*(\\{space}*\n)*\n*
return (keyword->value); return (keyword->value);
} }
else else
{
struct _defines *ptr;
for (ptr = defines; ptr; ptr = ptr->next)
{
if (strcmp(yytext, ptr->old) == 0)
{
struct _yy_buffer *yb;
yb = mm_alloc(sizeof(struct _yy_buffer));
yb->buffer = YY_CURRENT_BUFFER;
yb->lineno = yylineno;
yb->filename = strdup(input_filename);
yb->next = yy_buffer;
yy_buffer = yb;
yy_scan_string(ptr->new);
break;
}
}
if (ptr == NULL)
{ {
yylval.str = strdup((char*)yytext); yylval.str = strdup((char*)yytext);
return (IDENT); return (IDENT);
} }
} }
} }
{integer}/{space}*-{number} { }
<SQL>{integer}/{space}*-{number} {
char* endptr; char* endptr;
BEGIN(xm); BEGIN(xm);
...@@ -372,7 +398,7 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -372,7 +398,7 @@ cppline {space}*#.*(\\{space}*\n)*\n*
} }
return (ICONST); return (ICONST);
} }
{real}/{space}*-{number} { <SQL>{real}/{space}*-{number} {
char* endptr; char* endptr;
BEGIN(xm); BEGIN(xm);
...@@ -382,7 +408,7 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -382,7 +408,7 @@ cppline {space}*#.*(\\{space}*\n)*\n*
yyerror("ERROR: Bad float8 input"); yyerror("ERROR: Bad float8 input");
return (FCONST); return (FCONST);
} }
{integer} { <SQL>{integer} {
char* endptr; char* endptr;
errno = 0; errno = 0;
...@@ -398,7 +424,7 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -398,7 +424,7 @@ cppline {space}*#.*(\\{space}*\n)*\n*
} }
return (ICONST); return (ICONST);
} }
{real} { <SQL>{real} {
char* endptr; char* endptr;
errno = 0; errno = 0;
...@@ -407,7 +433,39 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -407,7 +433,39 @@ cppline {space}*#.*(\\{space}*\n)*\n*
yyerror("ERROR: Bad float input"); yyerror("ERROR: Bad float input");
return (FCONST); return (FCONST);
} }
<C>{integer}/{space}*-{number} {
char* endptr;
BEGIN(xm);
errno = 0;
yylval.ival = strtol((char *)yytext,&endptr,10);
if (*endptr != '\0' || errno == ERANGE)
{
errno = 0;
yylval.dval = strtod(((char *)yytext),&endptr);
if (*endptr != '\0' || errno == ERANGE)
yyerror("ERROR: Bad integer input");
yyerror("WARNING: Integer input is out of range; promoted to float");
return (FCONST);
}
return (ICONST);
}
<C>{integer} {
char* endptr;
errno = 0;
yylval.ival = strtol((char *)yytext,&endptr,10);
if (*endptr != '\0' || errno == ERANGE)
{
errno = 0;
yylval.dval = strtod(((char *)yytext),&endptr);
if (*endptr != '\0' || errno == ERANGE)
yyerror("ERROR: Bad integer input");
yyerror("WARNING: Integer input is out of range; promoted to float");
return (FCONST);
}
return (ICONST);
}
<SQL>:{identifier}(("->"|\.){identifier})* { <SQL>:{identifier}(("->"|\.){identifier})* {
yylval.str = strdup((char*)yytext+1); yylval.str = strdup((char*)yytext+1);
return(CVARIABLE); return(CVARIABLE);
...@@ -431,16 +489,39 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -431,16 +489,39 @@ cppline {space}*#.*(\\{space}*\n)*\n*
return (keyword->value); return (keyword->value);
} }
else else
{
struct _defines *ptr;
for (ptr = defines; ptr; ptr = ptr->next)
{
if (strcmp(yytext, ptr->old) == 0)
{
struct _yy_buffer *yb;
yb = mm_alloc(sizeof(struct _yy_buffer));
yb->buffer = YY_CURRENT_BUFFER;
yb->lineno = yylineno;
yb->filename = strdup(input_filename);
yb->next = yy_buffer;
yy_buffer = yb;
yy_scan_string(ptr->new);
break;
}
}
if (ptr == NULL)
{ {
yylval.str = strdup((char*)yytext); yylval.str = strdup((char*)yytext);
return (IDENT); return (IDENT);
} }
} }
} }
}
<SQL>{space} { /* ignore */ } <SQL>{space} { /* ignore */ }
<SQL>";" { BEGIN C; return SQL_SEMI; } <SQL>";" { BEGIN C; return SQL_SEMI; }
<SQL>{other} { return (yytext[0]); } <SQL>{other} { return (yytext[0]); }
<C>{exec}{space}{sql} { BEGIN SQL; return SQL_START; } <C>{exec}{space}{sql} { BEGIN SQL; return SQL_START; }
<C>{ccomment} { /* ignore */ } <C>{ccomment} { /* ignore */ }
<C>{cppline} { <C>{cppline} {
...@@ -455,11 +536,35 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -455,11 +536,35 @@ cppline {space}*#.*(\\{space}*\n)*\n*
return (keyword->value); return (keyword->value);
} }
else else
{
struct _defines *ptr;
for (ptr = defines; ptr; ptr = ptr->next)
{
if (strcmp(yytext, ptr->old) == 0)
{
struct _yy_buffer *yb;
yb = mm_alloc(sizeof(struct _yy_buffer));
yb->buffer = YY_CURRENT_BUFFER;
yb->lineno = yylineno;
yb->filename = strdup(input_filename);
yb->next = yy_buffer;
yy_buffer = yb;
yy_scan_string(ptr->new);
break;
}
}
if (ptr == NULL)
{ {
yylval.str = strdup((char*)yytext); yylval.str = strdup((char*)yytext);
return (IDENT); return (IDENT);
} }
} }
}
<C>";" { return(';'); } <C>";" { return(';'); }
<C>"," { return(','); } <C>"," { return(','); }
<C>"*" { return('*'); } <C>"*" { return('*'); }
...@@ -470,6 +575,45 @@ cppline {space}*#.*(\\{space}*\n)*\n* ...@@ -470,6 +575,45 @@ cppline {space}*#.*(\\{space}*\n)*\n*
<C>\] { return(']'); } <C>\] { return(']'); }
<C>\= { return('='); } <C>\= { return('='); }
<C>{other} { return (S_ANYTHING); } <C>{other} { return (S_ANYTHING); }
<C>{exec}{space}{sql}{space}{define} {BEGIN(def_ident);}
<def_ident>{space} {}
<def_ident>{identifier} {
old = strdup(yytext);
BEGIN(def);
llen = 0;
*literal = '\0';
}
<def>{space} /* eat the whitespace */
<def>";" {
struct _defines *ptr, *this;
for (ptr = defines; ptr != NULL; ptr = ptr->next)
{
if (strcmp(old, ptr->old) == 0)
{
free(ptr->new);
ptr->new = strdup(scanstr(literal));
}
}
if (ptr == NULL)
{
this = (struct _defines *) mm_alloc(sizeof(struct _defines));
/* initial definition */
this->old = old;
this->new = strdup(scanstr(literal));
this->next = defines;
defines = this;
}
BEGIN(C);
}
<def>[^";"] {
if ((llen+yyleng) > (MAX_PARSE_BUFFER - 1))
yyerror("ERROR: define statement parse buffer exceeded");
memcpy(literal+llen, yytext, yyleng+1);
llen += yyleng;
}
<C>{exec}{space}{sql}{space}{include} { BEGIN(incl); } <C>{exec}{space}{sql}{space}{include} { BEGIN(incl); }
<incl>{space} /* eat the whitespace */ <incl>{space} /* eat the whitespace */
<incl>[^ \t\n]+ { /* got the include file name */ <incl>[^ \t\n]+ { /* got the include file name */
......
...@@ -620,7 +620,7 @@ output_statement(char * stmt, int mode) ...@@ -620,7 +620,7 @@ output_statement(char * stmt, int mode)
%type <str> ColId default_expr ColQualifier columnDef ColQualList %type <str> ColId default_expr ColQualifier columnDef ColQualList
%type <str> ColConstraint ColConstraintElem default_list NumericOnly FloatOnly %type <str> ColConstraint ColConstraintElem default_list NumericOnly FloatOnly
%type <str> OptTableElementList OptTableElement TableConstraint %type <str> OptTableElementList OptTableElement TableConstraint
%type <str> ConstraintElem key_actions constraint_list TypeId %type <str> ConstraintElem key_actions constraint_list
%type <str> res_target_list res_target_el res_target_list2 %type <str> res_target_list res_target_el res_target_list2
%type <str> res_target_el2 opt_id relation_name database_name %type <str> res_target_el2 opt_id relation_name database_name
%type <str> access_method attr_name class index_name name func_name %type <str> access_method attr_name class index_name name func_name
...@@ -636,12 +636,12 @@ output_statement(char * stmt, int mode) ...@@ -636,12 +636,12 @@ output_statement(char * stmt, int mode)
%type <str> SelectStmt union_clause select_list SubSelect result %type <str> SelectStmt union_clause select_list SubSelect result
%type <str> opt_table opt_union opt_unique sort_clause sortby_list %type <str> opt_table opt_union opt_unique sort_clause sortby_list
%type <str> sortby OptUseOp opt_inh_star relation_name_list name_list %type <str> sortby OptUseOp opt_inh_star relation_name_list name_list
%type <str> group_clause groupby_list groupby having_clause from_clause %type <str> group_clause having_clause from_clause c_list
%type <str> from_list from_val join_expr join_outer join_spec join_list %type <str> from_list from_val join_expr join_outer join_spec join_list
%type <str> join_using where_clause relation_expr row_op sub_type %type <str> join_using where_clause relation_expr row_op sub_type
%type <str> opt_column_list insert_rest InsertStmt OptimizableStmt %type <str> opt_column_list insert_rest InsertStmt OptimizableStmt
%type <str> columnList DeleteStmt LockStmt UpdateStmt CursorStmt %type <str> columnList DeleteStmt LockStmt UpdateStmt CursorStmt
%type <str> NotifyStmt columnElem copy_dirn SubUnion %type <str> NotifyStmt columnElem copy_dirn SubUnion c_expr
%type <str> copy_delimiter ListenStmt CopyStmt copy_file_name opt_binary %type <str> copy_delimiter ListenStmt CopyStmt copy_file_name opt_binary
%type <str> opt_with_copy FetchStmt opt_direction fetch_how_many opt_portal_name %type <str> opt_with_copy FetchStmt opt_direction fetch_how_many opt_portal_name
%type <str> ClosePortalStmt DestroyStmt VacuumStmt opt_verbose %type <str> ClosePortalStmt DestroyStmt VacuumStmt opt_verbose
...@@ -652,7 +652,7 @@ output_statement(char * stmt, int mode) ...@@ -652,7 +652,7 @@ output_statement(char * stmt, int mode)
%type <str> def_elem def_list definition def_name def_type DefineStmt %type <str> def_elem def_list definition def_name def_type DefineStmt
%type <str> opt_instead event event_object OptStmtMulti OptStmtBlock %type <str> opt_instead event event_object OptStmtMulti OptStmtBlock
%type <str> OptStmtList RuleStmt opt_column opt_name oper_argtypes %type <str> OptStmtList RuleStmt opt_column opt_name oper_argtypes
%type <str> MathOp RemoveOperStmt RemoveFuncStmt aggr_argtype %type <str> MathOp RemoveFuncStmt aggr_argtype
%type <str> RemoveAggrStmt remove_type RemoveStmt ExtendStmt RecipeStmt %type <str> RemoveAggrStmt remove_type RemoveStmt ExtendStmt RecipeStmt
%type <str> RemoveOperStmt RenameStmt all_Op user_valid_clause %type <str> RemoveOperStmt RenameStmt all_Op user_valid_clause
%type <str> VariableSetStmt var_value zone_value VariableShowStmt %type <str> VariableSetStmt var_value zone_value VariableShowStmt
...@@ -661,7 +661,7 @@ output_statement(char * stmt, int mode) ...@@ -661,7 +661,7 @@ output_statement(char * stmt, int mode)
%type <str> user_createuser_clause user_group_list user_group_clause %type <str> user_createuser_clause user_group_list user_group_clause
%type <str> CreateUserStmt AlterUserStmt CreateSeqStmt OptSeqList %type <str> CreateUserStmt AlterUserStmt CreateSeqStmt OptSeqList
%type <str> OptSeqElem TriggerForSpec TriggerForOpt TriggerForType %type <str> OptSeqElem TriggerForSpec TriggerForOpt TriggerForType
%type <str> TriggerFuncArgs DropTrigStmt TriggerOneEvent TriggerEvents %type <str> DropTrigStmt TriggerOneEvent TriggerEvents
%type <str> TriggerActionTime CreateTrigStmt DropPLangStmt PLangTrusted %type <str> TriggerActionTime CreateTrigStmt DropPLangStmt PLangTrusted
%type <str> CreatePLangStmt IntegerOnly TriggerFuncArgs TriggerFuncArg %type <str> CreatePLangStmt IntegerOnly TriggerFuncArgs TriggerFuncArg
%type <str> ViewStmt LoadStmt CreatedbStmt opt_database1 opt_database2 location %type <str> ViewStmt LoadStmt CreatedbStmt opt_database1 opt_database2 location
...@@ -669,7 +669,7 @@ output_statement(char * stmt, int mode) ...@@ -669,7 +669,7 @@ output_statement(char * stmt, int mode)
%type <str> GrantStmt privileges operation_commalist operation %type <str> GrantStmt privileges operation_commalist operation
%type <str> ECPGWhenever ECPGConnect connection_target ECPGOpen open_opts %type <str> ECPGWhenever ECPGConnect connection_target ECPGOpen open_opts
%type <str> indicator ECPGExecute c_expr variable_list dotext %type <str> indicator ECPGExecute ecpg_expr dotext
%type <str> storage_clause opt_initializer vartext c_anything blockstart %type <str> storage_clause opt_initializer vartext c_anything blockstart
%type <str> blockend variable_list variable var_anything do_anything %type <str> blockend variable_list variable var_anything do_anything
%type <str> opt_pointer cvariable ECPGDisconnect dis_name %type <str> opt_pointer cvariable ECPGDisconnect dis_name
...@@ -756,6 +756,7 @@ stmt: AddAttrStmt { output_statement($1, 0); } ...@@ -756,6 +756,7 @@ stmt: AddAttrStmt { output_statement($1, 0); }
| VariableShowStmt { output_statement($1, 0); } | VariableShowStmt { output_statement($1, 0); }
| VariableResetStmt { output_statement($1, 0); } | VariableResetStmt { output_statement($1, 0); }
| ECPGConnect { | ECPGConnect {
fprintf(yyout, "no_auto_trans = %d;\n", no_auto_trans);
fprintf(yyout, "ECPGconnect(__LINE__, %s);", $1); fprintf(yyout, "ECPGconnect(__LINE__, %s);", $1);
whenever_action(0); whenever_action(0);
free($1); free($1);
...@@ -1307,6 +1308,8 @@ constraint_expr: AexprConst ...@@ -1307,6 +1308,8 @@ constraint_expr: AexprConst
{ $$ = cat3_str($1, $2, $3); } { $$ = cat3_str($1, $2, $3); }
| constraint_expr LIKE constraint_expr | constraint_expr LIKE constraint_expr
{ $$ = cat3_str($1, make1_str("like"), $3); } { $$ = cat3_str($1, make1_str("like"), $3); }
| constraint_expr NOT LIKE constraint_expr
{ $$ = cat3_str($1, make1_str("not like"), $4); }
| constraint_expr AND constraint_expr | constraint_expr AND constraint_expr
{ $$ = cat3_str($1, make1_str("and"), $3); } { $$ = cat3_str($1, make1_str("and"), $3); }
| constraint_expr OR constraint_expr | constraint_expr OR constraint_expr
...@@ -1333,7 +1336,28 @@ constraint_expr: AexprConst ...@@ -1333,7 +1336,28 @@ constraint_expr: AexprConst
{ $$ = cat2_str($1, make1_str("is not true")); } { $$ = cat2_str($1, make1_str("is not true")); }
| constraint_expr IS NOT FALSE_P | constraint_expr IS NOT FALSE_P
{ $$ = cat2_str($1, make1_str("is not false")); } { $$ = cat2_str($1, make1_str("is not false")); }
| constraint_expr IN '(' c_list ')'
{ $$ = cat4_str($1, make1_str("in ("), $4, make1_str(")")); }
| constraint_expr NOT IN '(' c_list ')'
{ $$ = cat4_str($1, make1_str("not in ("), $5, make1_str(")")); }
| constraint_expr BETWEEN c_expr AND c_expr
{ $$ = cat5_str($1, make1_str("between"), $3, make1_str("and"), $5); }
| constraint_expr NOT BETWEEN c_expr AND c_expr
{ $$ = cat5_str($1, make1_str("not between"), $4, make1_str("and"), $6); }
; ;
c_list: c_list ',' c_expr
{
$$ = make3_str($1, make1_str(", "), $3);
}
| c_expr
{
$$ = $1;
}
c_expr: AexprConst
{
$$ = $1;
}
key_match: MATCH FULL { $$ = make1_str("match full"); } key_match: MATCH FULL { $$ = make1_str("match full"); }
| MATCH PARTIAL { $$ = make1_str("match partial"); } | MATCH PARTIAL { $$ = make1_str("match partial"); }
...@@ -2025,6 +2049,7 @@ RuleStmt: CREATE RULE name AS ...@@ -2025,6 +2049,7 @@ RuleStmt: CREATE RULE name AS
OptStmtList: NOTHING { $$ = make1_str("nothing"); } OptStmtList: NOTHING { $$ = make1_str("nothing"); }
| OptimizableStmt { $$ = $1; } | OptimizableStmt { $$ = $1; }
| '[' OptStmtBlock ']' { $$ = cat3_str(make1_str("["), $2, make1_str("]")); } | '[' OptStmtBlock ']' { $$ = cat3_str(make1_str("["), $2, make1_str("]")); }
| '(' OptStmtBlock ')' { $$ = cat3_str(make1_str("("), $2, make1_str(")")); }
; ;
OptStmtBlock: OptStmtMulti OptStmtBlock: OptStmtMulti
...@@ -2480,15 +2505,7 @@ sortby_list: sortby { $$ = $1; } ...@@ -2480,15 +2505,7 @@ sortby_list: sortby { $$ = $1; }
| sortby_list ',' sortby { $$ = cat3_str($1, make1_str(","), $3); } | sortby_list ',' sortby { $$ = cat3_str($1, make1_str(","), $3); }
; ;
sortby: ColId OptUseOp sortby: a_expr OptUseOp
{
$$ = cat2_str($1, $2);
}
| ColId '.' ColId OptUseOp
{
$$ = cat2_str(make3_str($1, make1_str("."), $3), $4);
}
| Iconst OptUseOp
{ {
$$ = cat2_str($1, $2); $$ = cat2_str($1, $2);
} }
...@@ -2521,28 +2538,10 @@ name_list: name ...@@ -2521,28 +2538,10 @@ name_list: name
{ $$ = cat3_str($1, make1_str(","), $3); } { $$ = cat3_str($1, make1_str(","), $3); }
; ;
group_clause: GROUP BY groupby_list { $$ = cat2_str(make1_str("groub by"), $3); } group_clause: GROUP BY expr_list { $$ = cat2_str(make1_str("groub by"), $3); }
| /*EMPTY*/ { $$ = make1_str(""); } | /*EMPTY*/ { $$ = make1_str(""); }
; ;
groupby_list: groupby { $$ = $1; }
| groupby_list ',' groupby { $$ = cat3_str($1, make1_str(","), $3); }
;
groupby: ColId
{
$$ = $1;
}
| ColId '.' ColId
{
$$ = make3_str($1, make1_str(","), $3);
}
| Iconst
{
$$ = $1;
}
;
having_clause: HAVING a_expr having_clause: HAVING a_expr
{ {
$$ = cat2_str(make1_str("having"), $2); $$ = cat2_str(make1_str("having"), $2);
...@@ -3410,11 +3409,11 @@ b_expr: attr opt_indirection ...@@ -3410,11 +3409,11 @@ b_expr: attr opt_indirection
{ $$ = make1_str(";;"); } { $$ = make1_str(";;"); }
; ;
opt_indirection: '[' c_expr ']' opt_indirection opt_indirection: '[' ecpg_expr ']' opt_indirection
{ {
$$ = cat4_str(make1_str("["), $2, make1_str("]"), $4); $$ = cat4_str(make1_str("["), $2, make1_str("]"), $4);
} }
| '[' c_expr ':' c_expr ']' opt_indirection | '[' ecpg_expr ':' ecpg_expr ']' opt_indirection
{ {
$$ = cat2_str(cat5_str(make1_str("["), $2, make1_str(":"), $4, make1_str("]")), $6); $$ = cat2_str(cat5_str(make1_str("["), $2, make1_str(":"), $4, make1_str("]")), $6);
} }
...@@ -4353,7 +4352,7 @@ action : SQL_CONTINUE { ...@@ -4353,7 +4352,7 @@ action : SQL_CONTINUE {
/* some other stuff for ecpg */ /* some other stuff for ecpg */
c_expr: attr opt_indirection ecpg_expr: attr opt_indirection
{ {
$$ = cat2_str($1, $2); $$ = cat2_str($1, $2);
} }
...@@ -4365,27 +4364,27 @@ c_expr: attr opt_indirection ...@@ -4365,27 +4364,27 @@ c_expr: attr opt_indirection
{ {
$$ = $1; $$ = $1;
} }
| '-' c_expr %prec UMINUS | '-' ecpg_expr %prec UMINUS
{ $$ = cat2_str(make1_str("-"), $2); } { $$ = cat2_str(make1_str("-"), $2); }
| a_expr '+' c_expr | a_expr '+' ecpg_expr
{ $$ = cat3_str($1, make1_str("+"), $3); } { $$ = cat3_str($1, make1_str("+"), $3); }
| a_expr '-' c_expr | a_expr '-' ecpg_expr
{ $$ = cat3_str($1, make1_str("-"), $3); } { $$ = cat3_str($1, make1_str("-"), $3); }
| a_expr '/' c_expr | a_expr '/' ecpg_expr
{ $$ = cat3_str($1, make1_str("/"), $3); } { $$ = cat3_str($1, make1_str("/"), $3); }
| a_expr '*' c_expr | a_expr '*' ecpg_expr
{ $$ = cat3_str($1, make1_str("*"), $3); } { $$ = cat3_str($1, make1_str("*"), $3); }
| a_expr '<' c_expr | a_expr '<' ecpg_expr
{ $$ = cat3_str($1, make1_str("<"), $3); } { $$ = cat3_str($1, make1_str("<"), $3); }
| a_expr '>' c_expr | a_expr '>' ecpg_expr
{ $$ = cat3_str($1, make1_str(">"), $3); } { $$ = cat3_str($1, make1_str(">"), $3); }
| a_expr '=' c_expr | a_expr '=' ecpg_expr
{ $$ = cat3_str($1, make1_str("="), $3); } { $$ = cat3_str($1, make1_str("="), $3); }
/* | ':' c_expr /* | ':' ecpg_expr
{ $$ = cat2_str(make1_str(":"), $2); }*/ { $$ = cat2_str(make1_str(":"), $2); }*/
| ';' c_expr | ';' ecpg_expr
{ $$ = cat2_str(make1_str(";"), $2); } { $$ = cat2_str(make1_str(";"), $2); }
| '|' c_expr | '|' ecpg_expr
{ $$ = cat2_str(make1_str("|"), $2); } { $$ = cat2_str(make1_str("|"), $2); }
| a_expr TYPECAST Typename | a_expr TYPECAST Typename
{ {
...@@ -4397,13 +4396,13 @@ c_expr: attr opt_indirection ...@@ -4397,13 +4396,13 @@ c_expr: attr opt_indirection
} }
| '(' a_expr_or_null ')' | '(' a_expr_or_null ')'
{ $$ = make3_str(make1_str("("), $2, make1_str(")")); } { $$ = make3_str(make1_str("("), $2, make1_str(")")); }
| a_expr Op c_expr | a_expr Op ecpg_expr
{ $$ = cat3_str($1, $2, $3); } { $$ = cat3_str($1, $2, $3); }
| a_expr LIKE c_expr | a_expr LIKE ecpg_expr
{ $$ = cat3_str($1, make1_str("like"), $3); } { $$ = cat3_str($1, make1_str("like"), $3); }
| a_expr NOT LIKE c_expr | a_expr NOT LIKE ecpg_expr
{ $$ = cat3_str($1, make1_str("not like"), $4); } { $$ = cat3_str($1, make1_str("not like"), $4); }
| Op c_expr | Op ecpg_expr
{ $$ = cat2_str($1, $2); } { $$ = cat2_str($1, $2); }
| a_expr Op | a_expr Op
{ $$ = cat2_str($1, $2); } { $$ = cat2_str($1, $2); }
...@@ -4621,11 +4620,11 @@ c_expr: attr opt_indirection ...@@ -4621,11 +4620,11 @@ c_expr: attr opt_indirection
{ {
$$ = make4_str($1, make1_str("=all("), $5, make1_str(")")); $$ = make4_str($1, make1_str("=all("), $5, make1_str(")"));
} }
| a_expr AND c_expr | a_expr AND ecpg_expr
{ $$ = cat3_str($1, make1_str("and"), $3); } { $$ = cat3_str($1, make1_str("and"), $3); }
| a_expr OR c_expr | a_expr OR ecpg_expr
{ $$ = cat3_str($1, make1_str("or"), $3); } { $$ = cat3_str($1, make1_str("or"), $3); }
| NOT c_expr | NOT ecpg_expr
{ $$ = cat2_str(make1_str("not"), $2); } { $$ = cat2_str(make1_str("not"), $2); }
| civariableonly | civariableonly
{ $$ = make1_str(";;"); } { $$ = make1_str(";;"); }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment