mirror of
https://github.com/postgres/postgres.git
synced 2025-06-25 01:02:05 +03:00
*** empty log message ***
This commit is contained in:
@ -814,5 +814,10 @@ Wed Feb 16 17:04:41 CET 2000
|
|||||||
|
|
||||||
- Apply patch by Christof Petig <christof.petig@wtal.de> that adds
|
- Apply patch by Christof Petig <christof.petig@wtal.de> that adds
|
||||||
descriptors.
|
descriptors.
|
||||||
|
|
||||||
|
Thu Feb 17 19:37:44 CET 2000
|
||||||
|
|
||||||
|
- Synced preproc.y with gram.y.
|
||||||
|
- Started to clean up preproc.y.
|
||||||
- Set library version to 3.1.0.
|
- Set library version to 3.1.0.
|
||||||
- Set ecpg version to 2.7.0.
|
- Set ecpg version to 2.7.0.
|
||||||
|
@ -26,6 +26,8 @@ Add a semantic check level, e.g. check if a table really exists.
|
|||||||
It would be nice if there was a alternative library using SPI functions
|
It would be nice if there was a alternative library using SPI functions
|
||||||
instead of libpq so we can write backend functions using ecpg.
|
instead of libpq so we can write backend functions using ecpg.
|
||||||
|
|
||||||
|
make ECPGnumeric_lvalue more accurate by using something like ECPGdump_a_*
|
||||||
|
|
||||||
Missing statements:
|
Missing statements:
|
||||||
- exec sql ifdef
|
- exec sql ifdef
|
||||||
- SQLSTATE
|
- SQLSTATE
|
||||||
|
@ -60,6 +60,8 @@ extern "C"
|
|||||||
bool ECPGdeallocate_desc(int line,const char *name);
|
bool ECPGdeallocate_desc(int line,const char *name);
|
||||||
bool ECPGallocate_desc(int line,const char *name);
|
bool ECPGallocate_desc(int line,const char *name);
|
||||||
void ECPGraise(int line,int code);
|
void ECPGraise(int line,int code);
|
||||||
|
bool ECPGget_desc_header(int, char *, int *);
|
||||||
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
|
15
src/interfaces/ecpg/lib/descriptor.c
Normal file
15
src/interfaces/ecpg/lib/descriptor.c
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
#include <ecpgtype.h>
|
||||||
|
#include <ecpglib.h>
|
||||||
|
|
||||||
|
bool
|
||||||
|
ECPGget_desc_header(int lineno, char * desc_name, int *count)
|
||||||
|
{
|
||||||
|
PGresult *ECPGresult = ECPGresultByDescriptor(lineno, desc_name);
|
||||||
|
|
||||||
|
if (!ECPGresult)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
*count = PQnfields(ECPGresult);
|
||||||
|
ECPGlog("ECPGget-desc_header: found %d sttributes.\n", *count);
|
||||||
|
return true;
|
||||||
|
}
|
@ -2,7 +2,7 @@
|
|||||||
*
|
*
|
||||||
* Copyright (c) 2000, Christof Petig <christof.petig@wtal.de>
|
* Copyright (c) 2000, Christof Petig <christof.petig@wtal.de>
|
||||||
*
|
*
|
||||||
* $Header: /cvsroot/pgsql/src/interfaces/ecpg/lib/Attic/dynamic.c,v 1.2 2000/02/17 19:48:41 meskes Exp $
|
* $Header: /cvsroot/pgsql/src/interfaces/ecpg/lib/Attic/dynamic.c,v 1.3 2000/02/18 14:34:05 meskes Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* I borrowed the include files from ecpglib.c, maybe we don't need all of them */
|
/* I borrowed the include files from ecpglib.c, maybe we don't need all of them */
|
||||||
@ -211,11 +211,15 @@ bool ECPGdo_descriptor(int line,const char *connection,
|
|||||||
PGresult *ECPGresultByDescriptor(int line,const char *name)
|
PGresult *ECPGresultByDescriptor(int line,const char *name)
|
||||||
{
|
{
|
||||||
struct descriptor *i;
|
struct descriptor *i;
|
||||||
|
|
||||||
for (i = all_descriptors; i != NULL; i = i->next)
|
for (i = all_descriptors; i != NULL; i = i->next)
|
||||||
{ if (!strcmp(name,i->name)) return i->result;
|
{
|
||||||
|
if (!strcmp(name, i->name)) return i->result;
|
||||||
}
|
}
|
||||||
|
|
||||||
ECPGraise(line,ECPG_UNKNOWN_DESCRIPTOR);
|
ECPGraise(line,ECPG_UNKNOWN_DESCRIPTOR);
|
||||||
return 0;
|
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -249,9 +253,11 @@ bool ECPGallocate_desc(int line,const char *name)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void ECPGraise(int line, int code)
|
void ECPGraise(int line, int code)
|
||||||
{ sqlca.sqlcode=code;
|
{
|
||||||
|
sqlca.sqlcode=code;
|
||||||
switch (code)
|
switch (code)
|
||||||
{ case ECPG_NOT_FOUND:
|
{
|
||||||
|
case ECPG_NOT_FOUND:
|
||||||
snprintf(sqlca.sqlerrm.sqlerrmc,sizeof(sqlca.sqlerrm.sqlerrmc),
|
snprintf(sqlca.sqlerrm.sqlerrmc,sizeof(sqlca.sqlerrm.sqlerrmc),
|
||||||
"No data found line %d.",line);
|
"No data found line %d.",line);
|
||||||
break;
|
break;
|
||||||
|
@ -9,7 +9,7 @@ CFLAGS+=-I../include -DMAJOR_VERSION=$(MAJOR_VERSION) \
|
|||||||
-DMINOR_VERSION=$(MINOR_VERSION) -DPATCHLEVEL=$(PATCHLEVEL) \
|
-DMINOR_VERSION=$(MINOR_VERSION) -DPATCHLEVEL=$(PATCHLEVEL) \
|
||||||
-DINCLUDE_PATH=\"$(HEADERDIR)\" -g
|
-DINCLUDE_PATH=\"$(HEADERDIR)\" -g
|
||||||
|
|
||||||
OBJ=preproc.o pgc.o type.o ecpg.o ecpg_keywords.o \
|
OBJ=preproc.o pgc.o type.o ecpg.o ecpg_keywords.o output.o\
|
||||||
keywords.o c_keywords.o ../lib/typename.o descriptor.o variable.o
|
keywords.o c_keywords.o ../lib/typename.o descriptor.o variable.o
|
||||||
|
|
||||||
all:: ecpg
|
all:: ecpg
|
||||||
|
@ -25,8 +25,10 @@ void push_assignment(char *var,char *value)
|
|||||||
|
|
||||||
static void
|
static void
|
||||||
drop_assignments(void)
|
drop_assignments(void)
|
||||||
{ while (assignments)
|
{
|
||||||
{ struct assignment *old_head=assignments;
|
while (assignments)
|
||||||
|
{
|
||||||
|
struct assignment *old_head = assignments;
|
||||||
|
|
||||||
assignments = old_head->next;
|
assignments = old_head->next;
|
||||||
free(old_head->variable);
|
free(old_head->variable);
|
||||||
@ -35,9 +37,9 @@ drop_assignments(void)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* XXX: these should be more accurate (consider ECPGdump_a_* ) */
|
|
||||||
static void ECPGnumeric_lvalue(FILE *f,char *name)
|
static void ECPGnumeric_lvalue(FILE *f,char *name)
|
||||||
{ const struct variable *v=find_variable(name);
|
{
|
||||||
|
const struct variable *v=find_variable(name);
|
||||||
|
|
||||||
switch(v->type->typ)
|
switch(v->type->typ)
|
||||||
{
|
{
|
||||||
@ -167,30 +169,94 @@ static void ECPGdata_assignment(char *variable,char *index_plus_1)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* descriptor name lookup
|
||||||
|
*/
|
||||||
|
|
||||||
|
static struct descriptor *descriptors;
|
||||||
|
|
||||||
|
void add_descriptor(char *name,char *connection)
|
||||||
|
{
|
||||||
|
struct descriptor *new=(struct descriptor *)mm_alloc(sizeof(struct descriptor));
|
||||||
|
|
||||||
|
new->next=descriptors;
|
||||||
|
new->name=mm_alloc(strlen(name)+1);
|
||||||
|
strcpy(new->name,name);
|
||||||
|
if (connection)
|
||||||
|
{ new->connection=mm_alloc(strlen(connection)+1);
|
||||||
|
strcpy(new->connection,connection);
|
||||||
|
}
|
||||||
|
else new->connection=connection;
|
||||||
|
descriptors=new;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
drop_descriptor(char *name,char *connection)
|
||||||
|
{
|
||||||
|
struct descriptor *i;
|
||||||
|
struct descriptor **lastptr=&descriptors;
|
||||||
|
|
||||||
|
for (i=descriptors;i;lastptr=&i->next,i=i->next)
|
||||||
|
{
|
||||||
|
if (!strcmp(name,i->name))
|
||||||
|
{
|
||||||
|
if ((!connection && !i->connection)
|
||||||
|
|| (connection && i->connection
|
||||||
|
&& !strcmp(connection,i->connection)))
|
||||||
|
{
|
||||||
|
*lastptr=i->next;
|
||||||
|
if (i->connection) free(i->connection);
|
||||||
|
free(i->name);
|
||||||
|
free(i);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
snprintf(errortext,sizeof errortext,"unknown descriptor %s",name);
|
||||||
|
mmerror(ET_WARN,errortext);
|
||||||
|
}
|
||||||
|
|
||||||
|
struct descriptor
|
||||||
|
*lookup_descriptor(char *name,char *connection)
|
||||||
|
{
|
||||||
|
struct descriptor *i;
|
||||||
|
|
||||||
|
for (i=descriptors;i;i=i->next)
|
||||||
|
{
|
||||||
|
if (!strcmp(name,i->name))
|
||||||
|
{
|
||||||
|
if ((!connection && !i->connection)
|
||||||
|
|| (connection && i->connection
|
||||||
|
&& !strcmp(connection,i->connection)))
|
||||||
|
{
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
snprintf(errortext,sizeof errortext,"unknown descriptor %s",name);
|
||||||
|
mmerror(ET_WARN,errortext);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
output_get_descr_header(char *desc_name)
|
output_get_descr_header(char *desc_name)
|
||||||
{
|
{
|
||||||
struct assignment *results;
|
struct assignment *results;
|
||||||
|
|
||||||
fprintf(yyout,"{\tPGresult *ECPGresult=ECPGresultByDescriptor(%d, \"%s\");\n" ,yylineno,desc_name);
|
fprintf(yyout, "{ ECPGget_desc_header(%d, \"%s\", &(", yylineno, desc_name);
|
||||||
fputs("\tif (ECPGresult)\n\t{",yyout);
|
|
||||||
for (results = assignments; results != NULL; results = results->next)
|
for (results = assignments; results != NULL; results = results->next)
|
||||||
{
|
{
|
||||||
if (!strcasecmp(results->value, "count"))
|
if (!strcasecmp(results->value, "count"))
|
||||||
{
|
|
||||||
fputs("\t\t",yyout);
|
|
||||||
ECPGnumeric_lvalue(yyout,results->variable);
|
ECPGnumeric_lvalue(yyout,results->variable);
|
||||||
fputs("=PQnfields(ECPGresult);\n",yyout);
|
|
||||||
}
|
|
||||||
else
|
else
|
||||||
{ snprintf(errortext, sizeof errortext, "unknown descriptor header item '%s'", results->value);
|
{ snprintf(errortext, sizeof errortext, "unknown descriptor header item '%s'", results->value);
|
||||||
mmerror(ET_WARN, errortext);
|
mmerror(ET_WARN, errortext);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
drop_assignments();
|
|
||||||
fputs("}",yyout);
|
|
||||||
|
|
||||||
whenever_action(2|1);
|
drop_assignments();
|
||||||
|
fprintf(yyout, "));\n");
|
||||||
|
whenever_action(3);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -305,96 +371,3 @@ output_get_descr(char *desc_name)
|
|||||||
|
|
||||||
whenever_action(2|1);
|
whenever_action(2|1);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* descriptor name lookup
|
|
||||||
*/
|
|
||||||
|
|
||||||
static struct descriptor *descriptors;
|
|
||||||
|
|
||||||
void add_descriptor(char *name,char *connection)
|
|
||||||
{
|
|
||||||
struct descriptor *new=(struct descriptor *)mm_alloc(sizeof(struct descriptor));
|
|
||||||
|
|
||||||
new->next=descriptors;
|
|
||||||
new->name=mm_alloc(strlen(name)+1);
|
|
||||||
strcpy(new->name,name);
|
|
||||||
if (connection)
|
|
||||||
{ new->connection=mm_alloc(strlen(connection)+1);
|
|
||||||
strcpy(new->connection,connection);
|
|
||||||
}
|
|
||||||
else new->connection=connection;
|
|
||||||
descriptors=new;
|
|
||||||
}
|
|
||||||
|
|
||||||
void drop_descriptor(char *name,char *connection)
|
|
||||||
{
|
|
||||||
struct descriptor *i;
|
|
||||||
struct descriptor **lastptr=&descriptors;
|
|
||||||
|
|
||||||
for (i=descriptors;i;lastptr=&i->next,i=i->next)
|
|
||||||
{
|
|
||||||
if (!strcmp(name,i->name))
|
|
||||||
{
|
|
||||||
if ((!connection && !i->connection)
|
|
||||||
|| (connection && i->connection
|
|
||||||
&& !strcmp(connection,i->connection)))
|
|
||||||
{
|
|
||||||
*lastptr=i->next;
|
|
||||||
if (i->connection) free(i->connection);
|
|
||||||
free(i->name);
|
|
||||||
free(i);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
snprintf(errortext,sizeof errortext,"unknown descriptor %s",name);
|
|
||||||
mmerror(ET_WARN,errortext);
|
|
||||||
}
|
|
||||||
|
|
||||||
struct descriptor *lookup_descriptor(char *name,char *connection)
|
|
||||||
{
|
|
||||||
struct descriptor *i;
|
|
||||||
|
|
||||||
for (i=descriptors;i;i=i->next)
|
|
||||||
{
|
|
||||||
if (!strcmp(name,i->name))
|
|
||||||
{
|
|
||||||
if ((!connection && !i->connection)
|
|
||||||
|| (connection && i->connection
|
|
||||||
&& !strcmp(connection,i->connection)))
|
|
||||||
{
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
snprintf(errortext,sizeof errortext,"unknown descriptor %s",name);
|
|
||||||
mmerror(ET_WARN,errortext);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
output_statement_desc(char * stmt, int mode)
|
|
||||||
{
|
|
||||||
int i, j=strlen(stmt);
|
|
||||||
|
|
||||||
fprintf(yyout, "{ ECPGdo_descriptor(__LINE__, %s, \"%s\", \"",
|
|
||||||
connection ? connection : "NULL", descriptor_name);
|
|
||||||
|
|
||||||
/* do this char by char as we have to filter '\"' */
|
|
||||||
for (i = 0;i < j; i++) {
|
|
||||||
if (stmt[i] != '\"')
|
|
||||||
fputc(stmt[i], yyout);
|
|
||||||
else
|
|
||||||
fputs("\\\"", yyout);
|
|
||||||
}
|
|
||||||
|
|
||||||
fputs("\");", yyout);
|
|
||||||
|
|
||||||
mode |= 2;
|
|
||||||
whenever_action(mode);
|
|
||||||
free(stmt);
|
|
||||||
if (connection != NULL)
|
|
||||||
free(connection);
|
|
||||||
free(descriptor_name);
|
|
||||||
}
|
|
||||||
|
@ -5,6 +5,7 @@
|
|||||||
/* defines */
|
/* defines */
|
||||||
|
|
||||||
#define STRUCT_DEPTH 128
|
#define STRUCT_DEPTH 128
|
||||||
|
#define EMPTY make_str("")
|
||||||
|
|
||||||
/* variables */
|
/* variables */
|
||||||
|
|
||||||
@ -12,15 +13,13 @@ extern int braces_open,
|
|||||||
autocommit,
|
autocommit,
|
||||||
ret_value,
|
ret_value,
|
||||||
struct_level;
|
struct_level;
|
||||||
extern char *yytext,
|
|
||||||
errortext[128];
|
|
||||||
extern int yylineno,
|
|
||||||
yyleng;
|
|
||||||
extern FILE *yyin,
|
|
||||||
*yyout;
|
|
||||||
extern char *descriptor_index;
|
extern char *descriptor_index;
|
||||||
extern char *descriptor_name;
|
extern char *descriptor_name;
|
||||||
extern char *connection;
|
extern char *connection;
|
||||||
|
extern char *input_filename;;
|
||||||
|
extern char *yytext, errortext[128];
|
||||||
|
extern int yylineno, yyleng;
|
||||||
|
extern FILE *yyin, *yyout;
|
||||||
|
|
||||||
extern struct _include_path *include_paths;
|
extern struct _include_path *include_paths;
|
||||||
extern struct cursor *cur;
|
extern struct cursor *cur;
|
||||||
@ -36,9 +35,12 @@ extern struct descriptor *descriptors;
|
|||||||
|
|
||||||
/* functions */
|
/* functions */
|
||||||
|
|
||||||
extern void output_line_number(void);
|
|
||||||
extern void lex_init(void);
|
extern void lex_init(void);
|
||||||
extern char *input_filename;
|
extern char *make_str(const char *);
|
||||||
|
extern void output_line_number(void);
|
||||||
|
extern void output_statement(char *, int, char *);
|
||||||
|
extern void output_simple_statement(char *);
|
||||||
|
extern char *hashline_number(void);
|
||||||
extern int yyparse(void);
|
extern int yyparse(void);
|
||||||
extern int yylex(void);
|
extern int yylex(void);
|
||||||
extern void yyerror(char *);
|
extern void yyerror(char *);
|
||||||
@ -55,7 +57,6 @@ extern void whenever_action(int);
|
|||||||
extern void add_descriptor(char *,char *);
|
extern void add_descriptor(char *,char *);
|
||||||
extern void drop_descriptor(char *,char *);
|
extern void drop_descriptor(char *,char *);
|
||||||
extern struct descriptor *lookup_descriptor(char *,char *);
|
extern struct descriptor *lookup_descriptor(char *,char *);
|
||||||
extern void output_statement_desc(char *, int);
|
|
||||||
extern void add_variable(struct arguments ** , struct variable * , struct variable *);
|
extern void add_variable(struct arguments ** , struct variable * , struct variable *);
|
||||||
extern void dump_variables(struct arguments *, int);
|
extern void dump_variables(struct arguments *, int);
|
||||||
extern struct typedefs *get_typedef(char *);
|
extern struct typedefs *get_typedef(char *);
|
||||||
|
126
src/interfaces/ecpg/preproc/output.c
Normal file
126
src/interfaces/ecpg/preproc/output.c
Normal file
@ -0,0 +1,126 @@
|
|||||||
|
#include <stdarg.h>
|
||||||
|
|
||||||
|
#include "postgres.h"
|
||||||
|
#include "extern.h"
|
||||||
|
|
||||||
|
void
|
||||||
|
output_line_number()
|
||||||
|
{
|
||||||
|
if (input_filename)
|
||||||
|
fprintf(yyout, "\n#line %d \"%s\"\n", yylineno, input_filename);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
output_simple_statement(char *cmd)
|
||||||
|
{
|
||||||
|
fputs(cmd, yyout);
|
||||||
|
output_line_number();
|
||||||
|
free(cmd);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* store the whenever action here
|
||||||
|
*/
|
||||||
|
struct when when_error, when_nf, when_warn;
|
||||||
|
|
||||||
|
static void
|
||||||
|
print_action(struct when *w)
|
||||||
|
{
|
||||||
|
switch (w->code)
|
||||||
|
{
|
||||||
|
case W_SQLPRINT: fprintf(yyout, "sqlprint();");
|
||||||
|
break;
|
||||||
|
case W_GOTO: fprintf(yyout, "goto %s;", w->command);
|
||||||
|
break;
|
||||||
|
case W_DO: fprintf(yyout, "%s;", w->command);
|
||||||
|
break;
|
||||||
|
case W_STOP: fprintf(yyout, "exit (1);");
|
||||||
|
break;
|
||||||
|
case W_BREAK: fprintf(yyout, "break;");
|
||||||
|
break;
|
||||||
|
default: fprintf(yyout, "{/* %d not implemented yet */}", w->code);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
whenever_action(int mode)
|
||||||
|
{
|
||||||
|
if ((mode&1) == 1 && when_nf.code != W_NOTHING)
|
||||||
|
{
|
||||||
|
output_line_number();
|
||||||
|
fprintf(yyout, "\nif (sqlca.sqlcode == ECPG_NOT_FOUND) ");
|
||||||
|
print_action(&when_nf);
|
||||||
|
}
|
||||||
|
if (when_warn.code != W_NOTHING)
|
||||||
|
{
|
||||||
|
output_line_number();
|
||||||
|
fprintf(yyout, "\nif (sqlca.sqlwarn[0] == 'W') ");
|
||||||
|
print_action(&when_warn);
|
||||||
|
}
|
||||||
|
if (when_error.code != W_NOTHING)
|
||||||
|
{
|
||||||
|
output_line_number();
|
||||||
|
fprintf(yyout, "\nif (sqlca.sqlcode < 0) ");
|
||||||
|
print_action(&when_error);
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((mode&2) == 2)
|
||||||
|
fputc('}', yyout);
|
||||||
|
|
||||||
|
output_line_number();
|
||||||
|
}
|
||||||
|
|
||||||
|
char *
|
||||||
|
hashline_number(void)
|
||||||
|
{
|
||||||
|
if (input_filename)
|
||||||
|
{
|
||||||
|
char* line = mm_alloc(strlen("\n#line %d \"%s\"\n") + 21 + strlen(input_filename));
|
||||||
|
sprintf(line, "\n#line %d \"%s\"\n", yylineno, input_filename);
|
||||||
|
|
||||||
|
return line;
|
||||||
|
}
|
||||||
|
|
||||||
|
return EMPTY;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
output_statement(char * stmt, int mode, char *descriptor)
|
||||||
|
{
|
||||||
|
int i, j=strlen(stmt);
|
||||||
|
|
||||||
|
if (descriptor == NULL)
|
||||||
|
fprintf(yyout, "{ ECPGdo(__LINE__, %s, \"", connection ? connection : "NULL");
|
||||||
|
else
|
||||||
|
fprintf(yyout, "{ ECPGdo_descriptor(__LINE__, %s, \"%s\", \"",
|
||||||
|
connection ? connection : "NULL", descriptor);
|
||||||
|
|
||||||
|
/* do this char by char as we have to filter '\"' */
|
||||||
|
for (i = 0;i < j; i++) {
|
||||||
|
if (stmt[i] != '\"')
|
||||||
|
fputc(stmt[i], yyout);
|
||||||
|
else
|
||||||
|
fputs("\\\"", yyout);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (descriptor == NULL)
|
||||||
|
{
|
||||||
|
fputs("\", ", yyout);
|
||||||
|
|
||||||
|
/* dump variables to C file */
|
||||||
|
dump_variables(argsinsert, 1);
|
||||||
|
fputs("ECPGt_EOIT, ", yyout);
|
||||||
|
dump_variables(argsresult, 1);
|
||||||
|
fputs("ECPGt_EORT);", yyout);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
fputs("\");", yyout);
|
||||||
|
|
||||||
|
mode |= 2;
|
||||||
|
whenever_action(mode);
|
||||||
|
free(stmt);
|
||||||
|
if (connection != NULL)
|
||||||
|
free(connection);
|
||||||
|
}
|
||||||
|
|
@ -15,16 +15,15 @@
|
|||||||
#include "mb/pg_wchar.h"
|
#include "mb/pg_wchar.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define EMPTY make_str("")
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Variables containing simple states.
|
* Variables containing simple states.
|
||||||
*/
|
*/
|
||||||
int struct_level = 0;
|
int struct_level = 0;
|
||||||
|
int braces_open; /* brace level counter */
|
||||||
char errortext[128];
|
char errortext[128];
|
||||||
char *descriptor_index= NULL;
|
char *descriptor_index= NULL;
|
||||||
char *connection = NULL;
|
char *connection = NULL;
|
||||||
char *descriptor_name = NULL;
|
char *input_filename = NULL;
|
||||||
|
|
||||||
static int QueryIsRule = 0, ForUpdateNotAllowed = 0, FoundInto = 0;
|
static int QueryIsRule = 0, ForUpdateNotAllowed = 0, FoundInto = 0;
|
||||||
static int FoundSort = 0;
|
static int FoundSort = 0;
|
||||||
@ -47,7 +46,6 @@ struct ECPGtype ecpg_query = {ECPGt_char_variable, 0L, {NULL}};
|
|||||||
void
|
void
|
||||||
mmerror(enum errortype type, char * error)
|
mmerror(enum errortype type, char * error)
|
||||||
{
|
{
|
||||||
|
|
||||||
switch(type)
|
switch(type)
|
||||||
{
|
{
|
||||||
case ET_WARN:
|
case ET_WARN:
|
||||||
@ -63,86 +61,6 @@ mmerror(enum errortype type, char * error)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* Handle the filename and line numbering.
|
|
||||||
*/
|
|
||||||
char * input_filename = NULL;
|
|
||||||
|
|
||||||
void
|
|
||||||
output_line_number()
|
|
||||||
{
|
|
||||||
if (input_filename)
|
|
||||||
fprintf(yyout, "\n#line %d \"%s\"\n", yylineno, input_filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
output_simple_statement(char *cmd)
|
|
||||||
{
|
|
||||||
fputs(cmd, yyout);
|
|
||||||
output_line_number();
|
|
||||||
free(cmd);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* store the whenever action here
|
|
||||||
*/
|
|
||||||
struct when when_error, when_nf, when_warn;
|
|
||||||
|
|
||||||
static void
|
|
||||||
print_action(struct when *w)
|
|
||||||
{
|
|
||||||
switch (w->code)
|
|
||||||
{
|
|
||||||
case W_SQLPRINT: fprintf(yyout, "sqlprint();");
|
|
||||||
break;
|
|
||||||
case W_GOTO: fprintf(yyout, "goto %s;", w->command);
|
|
||||||
break;
|
|
||||||
case W_DO: fprintf(yyout, "%s;", w->command);
|
|
||||||
break;
|
|
||||||
case W_STOP: fprintf(yyout, "exit (1);");
|
|
||||||
break;
|
|
||||||
case W_BREAK: fprintf(yyout, "break;");
|
|
||||||
break;
|
|
||||||
default: fprintf(yyout, "{/* %d not implemented yet */}", w->code);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
whenever_action(int mode)
|
|
||||||
{
|
|
||||||
if ((mode&1) == 1 && when_nf.code != W_NOTHING)
|
|
||||||
{
|
|
||||||
output_line_number();
|
|
||||||
fprintf(yyout, "\nif (sqlca.sqlcode == ECPG_NOT_FOUND) ");
|
|
||||||
print_action(&when_nf);
|
|
||||||
}
|
|
||||||
if (when_warn.code != W_NOTHING)
|
|
||||||
{
|
|
||||||
output_line_number();
|
|
||||||
fprintf(yyout, "\nif (sqlca.sqlwarn[0] == 'W') ");
|
|
||||||
print_action(&when_warn);
|
|
||||||
}
|
|
||||||
if (when_error.code != W_NOTHING)
|
|
||||||
{
|
|
||||||
output_line_number();
|
|
||||||
fprintf(yyout, "\nif (sqlca.sqlcode < 0) ");
|
|
||||||
print_action(&when_error);
|
|
||||||
}
|
|
||||||
if ((mode&2) == 2)
|
|
||||||
fputc('}', yyout);
|
|
||||||
output_line_number();
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Handling of variables.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* brace level counter
|
|
||||||
*/
|
|
||||||
int braces_open;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* string concatenation
|
* string concatenation
|
||||||
*/
|
*/
|
||||||
@ -180,7 +98,7 @@ cat_str(int count, ...)
|
|||||||
return(res_str);
|
return(res_str);
|
||||||
}
|
}
|
||||||
|
|
||||||
static char *
|
char *
|
||||||
make_str(const char *str)
|
make_str(const char *str)
|
||||||
{
|
{
|
||||||
char * res_str = (char *)mm_alloc(strlen(str) + 1);
|
char * res_str = (char *)mm_alloc(strlen(str) + 1);
|
||||||
@ -225,49 +143,6 @@ make_name(void)
|
|||||||
return(name);
|
return(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
static char *
|
|
||||||
hashline_number()
|
|
||||||
{
|
|
||||||
if (input_filename)
|
|
||||||
{
|
|
||||||
char* line = mm_alloc(strlen("\n#line %d \"%s\"\n") + 21 + strlen(input_filename));
|
|
||||||
sprintf(line, "\n#line %d \"%s\"\n", yylineno, input_filename);
|
|
||||||
|
|
||||||
return line;
|
|
||||||
}
|
|
||||||
|
|
||||||
return EMPTY;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
output_statement(char * stmt, int mode)
|
|
||||||
{
|
|
||||||
int i, j=strlen(stmt);
|
|
||||||
|
|
||||||
fprintf(yyout, "{ ECPGdo(__LINE__, %s, \"", connection ? connection : "NULL");
|
|
||||||
|
|
||||||
/* do this char by char as we have to filter '\"' */
|
|
||||||
for (i = 0;i < j; i++) {
|
|
||||||
if (stmt[i] != '\"')
|
|
||||||
fputc(stmt[i], yyout);
|
|
||||||
else
|
|
||||||
fputs("\\\"", yyout);
|
|
||||||
}
|
|
||||||
|
|
||||||
fputs("\", ", yyout);
|
|
||||||
|
|
||||||
/* dump variables to C file*/
|
|
||||||
dump_variables(argsinsert, 1);
|
|
||||||
fputs("ECPGt_EOIT, ", yyout);
|
|
||||||
dump_variables(argsresult, 1);
|
|
||||||
fputs("ECPGt_EORT);", yyout);
|
|
||||||
mode |= 2;
|
|
||||||
whenever_action(mode);
|
|
||||||
free(stmt);
|
|
||||||
if (connection != NULL)
|
|
||||||
free(connection);
|
|
||||||
}
|
|
||||||
|
|
||||||
%}
|
%}
|
||||||
|
|
||||||
%union {
|
%union {
|
||||||
@ -279,6 +154,7 @@ output_statement(char * stmt, int mode)
|
|||||||
int tagname;
|
int tagname;
|
||||||
struct this_type type;
|
struct this_type type;
|
||||||
enum ECPGttype type_enum;
|
enum ECPGttype type_enum;
|
||||||
|
struct fetch_desc descriptor;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* special embedded SQL token */
|
/* special embedded SQL token */
|
||||||
@ -482,7 +358,8 @@ output_statement(char * stmt, int mode)
|
|||||||
%type <str> s_struct s_union union_type ECPGSetAutocommit on_off
|
%type <str> s_struct s_union union_type ECPGSetAutocommit on_off
|
||||||
%type <str> ECPGAllocateDescr ECPGDeallocateDescr
|
%type <str> ECPGAllocateDescr ECPGDeallocateDescr
|
||||||
%type <str> ECPGGetDescriptor ECPGGetDescriptorHeader
|
%type <str> ECPGGetDescriptor ECPGGetDescriptorHeader
|
||||||
%type <str> FetchDescriptorStmt
|
|
||||||
|
%type <descriptor> ECPGFetchDescStmt
|
||||||
|
|
||||||
%type <type_enum> simple_type signed_type unsigned_type varchar_type
|
%type <type_enum> simple_type signed_type unsigned_type varchar_type
|
||||||
|
|
||||||
@ -509,64 +386,63 @@ statement: ecpgstart opt_at stmt ';' { connection = NULL; }
|
|||||||
|
|
||||||
opt_at: SQL_AT connection_target { connection = $2; }
|
opt_at: SQL_AT connection_target { connection = $2; }
|
||||||
|
|
||||||
stmt: AlterTableStmt { output_statement($1, 0); }
|
stmt: AlterTableStmt { output_statement($1, 0, NULL); }
|
||||||
| AlterGroupStmt { output_statement($1, 0); }
|
| AlterGroupStmt { output_statement($1, 0, NULL); }
|
||||||
| AlterUserStmt { output_statement($1, 0); }
|
| AlterUserStmt { output_statement($1, 0, NULL); }
|
||||||
| ClosePortalStmt { output_statement($1, 0); }
|
| ClosePortalStmt { output_statement($1, 0, NULL); }
|
||||||
| CommentStmt { output_statement($1, 0); }
|
| CommentStmt { output_statement($1, 0, NULL); }
|
||||||
| CopyStmt { output_statement($1, 0); }
|
| CopyStmt { output_statement($1, 0, NULL); }
|
||||||
| CreateStmt { output_statement($1, 0); }
|
| CreateStmt { output_statement($1, 0, NULL); }
|
||||||
| CreateAsStmt { output_statement($1, 0); }
|
| CreateAsStmt { output_statement($1, 0, NULL); }
|
||||||
| CreateGroupStmt { output_statement($1, 0); }
|
| CreateGroupStmt { output_statement($1, 0, NULL); }
|
||||||
| CreateSeqStmt { output_statement($1, 0); }
|
| CreateSeqStmt { output_statement($1, 0, NULL); }
|
||||||
| CreatePLangStmt { output_statement($1, 0); }
|
| CreatePLangStmt { output_statement($1, 0, NULL); }
|
||||||
| CreateTrigStmt { output_statement($1, 0); }
|
| CreateTrigStmt { output_statement($1, 0, NULL); }
|
||||||
| CreateUserStmt { output_statement($1, 0); }
|
| CreateUserStmt { output_statement($1, 0, NULL); }
|
||||||
| ClusterStmt { output_statement($1, 0); }
|
| ClusterStmt { output_statement($1, 0, NULL); }
|
||||||
| DefineStmt { output_statement($1, 0); }
|
| DefineStmt { output_statement($1, 0, NULL); }
|
||||||
| DropStmt { output_statement($1, 0); }
|
| DropStmt { output_statement($1, 0, NULL); }
|
||||||
| TruncateStmt { output_statement($1, 0); }
|
| TruncateStmt { output_statement($1, 0, NULL); }
|
||||||
| DropGroupStmt { output_statement($1, 0); }
|
| DropGroupStmt { output_statement($1, 0, NULL); }
|
||||||
| DropPLangStmt { output_statement($1, 0); }
|
| DropPLangStmt { output_statement($1, 0, NULL); }
|
||||||
| DropTrigStmt { output_statement($1, 0); }
|
| DropTrigStmt { output_statement($1, 0, NULL); }
|
||||||
| DropUserStmt { output_statement($1, 0); }
|
| DropUserStmt { output_statement($1, 0, NULL); }
|
||||||
| ExtendStmt { output_statement($1, 0); }
|
| ExtendStmt { output_statement($1, 0, NULL); }
|
||||||
| ExplainStmt { output_statement($1, 0); }
|
| ExplainStmt { output_statement($1, 0, NULL); }
|
||||||
| FetchStmt { output_statement($1, 1); }
|
| FetchStmt { output_statement($1, 1, NULL); }
|
||||||
| FetchDescriptorStmt { output_statement_desc($1, 1); }
|
| GrantStmt { output_statement($1, 0, NULL); }
|
||||||
| GrantStmt { output_statement($1, 0); }
|
| IndexStmt { output_statement($1, 0, NULL); }
|
||||||
| IndexStmt { output_statement($1, 0); }
|
| ListenStmt { output_statement($1, 0, NULL); }
|
||||||
| ListenStmt { output_statement($1, 0); }
|
| UnlistenStmt { output_statement($1, 0, NULL); }
|
||||||
| UnlistenStmt { output_statement($1, 0); }
|
| LockStmt { output_statement($1, 0, NULL); }
|
||||||
| LockStmt { output_statement($1, 0); }
|
| ProcedureStmt { output_statement($1, 0, NULL); }
|
||||||
| ProcedureStmt { output_statement($1, 0); }
|
| RemoveAggrStmt { output_statement($1, 0, NULL); }
|
||||||
| RemoveAggrStmt { output_statement($1, 0); }
|
| RemoveOperStmt { output_statement($1, 0, NULL); }
|
||||||
| RemoveOperStmt { output_statement($1, 0); }
|
| RemoveFuncStmt { output_statement($1, 0, NULL); }
|
||||||
| RemoveFuncStmt { output_statement($1, 0); }
|
| RemoveStmt { output_statement($1, 0, NULL); }
|
||||||
| RemoveStmt { output_statement($1, 0); }
|
| RenameStmt { output_statement($1, 0, NULL); }
|
||||||
| RenameStmt { output_statement($1, 0); }
|
| RevokeStmt { output_statement($1, 0, NULL); }
|
||||||
| RevokeStmt { output_statement($1, 0); }
|
|
||||||
| OptimizableStmt {
|
| OptimizableStmt {
|
||||||
if (strncmp($1, "/* " , sizeof("/* ")-1) == 0)
|
if (strncmp($1, "/* " , sizeof("/* ")-1) == 0)
|
||||||
output_simple_statement($1);
|
output_simple_statement($1);
|
||||||
else
|
else
|
||||||
output_statement($1, 1);
|
output_statement($1, 1, NULL);
|
||||||
}
|
}
|
||||||
| RuleStmt { output_statement($1, 0); }
|
| RuleStmt { output_statement($1, 0, NULL); }
|
||||||
| TransactionStmt {
|
| TransactionStmt {
|
||||||
fprintf(yyout, "{ ECPGtrans(__LINE__, %s, \"%s\");", connection ? connection : "NULL", $1);
|
fprintf(yyout, "{ ECPGtrans(__LINE__, %s, \"%s\");", connection ? connection : "NULL", $1);
|
||||||
whenever_action(2);
|
whenever_action(2);
|
||||||
free($1);
|
free($1);
|
||||||
}
|
}
|
||||||
| ViewStmt { output_statement($1, 0); }
|
| ViewStmt { output_statement($1, 0, NULL); }
|
||||||
| LoadStmt { output_statement($1, 0); }
|
| LoadStmt { output_statement($1, 0, NULL); }
|
||||||
| CreatedbStmt { output_statement($1, 0); }
|
| CreatedbStmt { output_statement($1, 0, NULL); }
|
||||||
| DropdbStmt { output_statement($1, 0); }
|
| DropdbStmt { output_statement($1, 0, NULL); }
|
||||||
| VacuumStmt { output_statement($1, 0); }
|
| VacuumStmt { output_statement($1, 0, NULL); }
|
||||||
| VariableSetStmt { output_statement($1, 0); }
|
| VariableSetStmt { output_statement($1, 0, NULL); }
|
||||||
| VariableShowStmt { output_statement($1, 0); }
|
| VariableShowStmt { output_statement($1, 0, NULL); }
|
||||||
| VariableResetStmt { output_statement($1, 0); }
|
| VariableResetStmt { output_statement($1, 0, NULL); }
|
||||||
| ConstraintsSetStmt { output_statement($1, 0); }
|
| ConstraintsSetStmt { output_statement($1, 0, NULL); }
|
||||||
| ECPGAllocateDescr { fprintf(yyout,"ECPGallocate_desc(__LINE__, \"%s\");",$1);
|
| ECPGAllocateDescr { fprintf(yyout,"ECPGallocate_desc(__LINE__, \"%s\");",$1);
|
||||||
whenever_action(0);
|
whenever_action(0);
|
||||||
free($1);
|
free($1);
|
||||||
@ -606,9 +482,8 @@ stmt: AlterTableStmt { output_statement($1, 0); }
|
|||||||
whenever_action(2);
|
whenever_action(2);
|
||||||
free($1);
|
free($1);
|
||||||
}
|
}
|
||||||
| ECPGExecute {
|
| ECPGExecute { output_statement($1, 0, NULL); }
|
||||||
output_statement($1, 0);
|
| ECPGFetchDescStmt { output_statement($1.str, 1, $1.name); }
|
||||||
}
|
|
||||||
| ECPGFree {
|
| ECPGFree {
|
||||||
fprintf(yyout, "{ ECPGdeallocate(__LINE__, \"%s\");", $1);
|
fprintf(yyout, "{ ECPGdeallocate(__LINE__, \"%s\");", $1);
|
||||||
|
|
||||||
@ -4754,30 +4629,30 @@ ECPGGetDescriptor: SQL_GET SQL_DESCRIPTOR ident SQL_VALUE cvariable ECPGGetDescI
|
|||||||
*
|
*
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
FetchDescriptorStmt: FETCH direction fetch_how_many from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
ECPGFetchDescStmt: FETCH direction fetch_how_many from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
||||||
{
|
{
|
||||||
$$ = cat_str(5, make_str("fetch"), $2, $3, $4, $5);
|
$$.str = cat_str(5, make_str("fetch"), $2, $3, $4, $5);
|
||||||
descriptor_name=$9;
|
$$.name=$9;
|
||||||
}
|
}
|
||||||
| FETCH fetch_how_many from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
| FETCH fetch_how_many from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
||||||
{
|
{
|
||||||
$$ = cat_str(4, make_str("fetch"), $2, $3, $4);
|
$$.str = cat_str(4, make_str("fetch"), $2, $3, $4);
|
||||||
descriptor_name=$8;
|
$$.name=$8;
|
||||||
}
|
}
|
||||||
| FETCH direction from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
| FETCH direction from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
||||||
{
|
{
|
||||||
$$ = cat_str(4, make_str("fetch"), $2, $3, $4);
|
$$.str = cat_str(4, make_str("fetch"), $2, $3, $4);
|
||||||
descriptor_name=$8;
|
$$.name=$8;
|
||||||
}
|
}
|
||||||
| FETCH from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
| FETCH from_in name INTO SQL_SQL SQL_DESCRIPTOR ident
|
||||||
{
|
{
|
||||||
$$ = cat_str(3, make_str("fetch"), $2, $3);
|
$$.str = cat_str(3, make_str("fetch"), $2, $3);
|
||||||
descriptor_name=$7;
|
$$.name=$7;
|
||||||
}
|
}
|
||||||
| FETCH name INTO SQL_SQL SQL_DESCRIPTOR ident
|
| FETCH name INTO SQL_SQL SQL_DESCRIPTOR ident
|
||||||
{
|
{
|
||||||
$$ = cat2_str(make_str("fetch"), $2);
|
$$.str = cat2_str(make_str("fetch"), $2);
|
||||||
descriptor_name=$6;
|
$$.name=$6;
|
||||||
}
|
}
|
||||||
;
|
;
|
||||||
|
|
||||||
|
@ -154,3 +154,9 @@ struct assignment
|
|||||||
};
|
};
|
||||||
|
|
||||||
enum errortype {ET_WARN, ET_ERROR, ET_FATAL};
|
enum errortype {ET_WARN, ET_ERROR, ET_FATAL};
|
||||||
|
|
||||||
|
struct fetch_desc
|
||||||
|
{
|
||||||
|
char *str;
|
||||||
|
char *name;
|
||||||
|
};
|
||||||
|
Reference in New Issue
Block a user