Skip to content

Commit bbe9902

Browse files
author
Michael Meskes
committed
Parse forward definiton of structs.
1 parent 9e2a980 commit bbe9902

File tree

6 files changed

+163
-139
lines changed

6 files changed

+163
-139
lines changed

src/interfaces/ecpg/ChangeLog

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1449,6 +1449,10 @@ Tue May 27 13:29:28 CEST 2003
14491449
Tue May 27 16:33:36 CEST 2003
14501450

14511451
- Accept stdin/stdout as input/output file.
1452+
1453+
Thu May 29 13:58:25 CEST 2003
1454+
1455+
- ecpg should now be able to parse forward struct definition.
14521456
- Set ecpg version to 2.12.0.
14531457
- Set ecpg library to 3.4.2.
14541458
- Set pgtypes library to 1.0.0

src/interfaces/ecpg/preproc/pgc.l

Lines changed: 3 additions & 91 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
*
1313
*
1414
* IDENTIFICATION
15-
* $Header: /cvsroot/pgsql/src/interfaces/ecpg/preproc/pgc.l,v 1.111 2003/05/27 14:36:00 meskes Exp $
15+
* $Header: /cvsroot/pgsql/src/interfaces/ecpg/preproc/pgc.l,v 1.112 2003/05/29 12:00:21 meskes Exp $
1616
*
1717
*-------------------------------------------------------------------------
1818
*/
@@ -184,6 +184,7 @@ letter_or_digit [\200-\377_A-Za-z0-9]
184184

185185
identifier {letter}{letter_or_digit}*
186186

187+
array ({letter_or_digit}|[\+\-\*\%\/\(\)])*
187188
typecast "::"
188189

189190
/*
@@ -949,96 +950,7 @@ cppline {space}*#(.*\\{space})+.*
949950

950951
<incl>\<[^\>]+\>{space}*";"? { parse_include(); }
951952
<incl>{dquote}{xdinside}{dquote}{space}*";"? { parse_include(); }
952-
<incl>[^;\<\>\"]+";" {
953-
parse_include();
954-
#if 0
955-
/* got the include file name */
956-
struct _yy_buffer *yb;
957-
struct _include_path *ip;
958-
char inc_file[MAXPGPATH];
959-
unsigned int i;
960-
961-
yb = mm_alloc(sizeof(struct _yy_buffer));
962-
963-
yb->buffer = YY_CURRENT_BUFFER;
964-
yb->lineno = yylineno;
965-
yb->filename = input_filename;
966-
yb->next = yy_buffer;
967-
968-
yy_buffer = yb;
969-
970-
/*
971-
* skip the ";" and trailing whitespace. Note that yytext contains
972-
* at least one non-space character plus the ";"
973-
*/
974-
for ( i = strlen(yytext)-2;
975-
i > 0 && isspace((unsigned char) yytext[i]);
976-
i-- )
977-
{}
978-
979-
yytext[i+1] = '\0';
980-
yyin = NULL;
981-
982-
/* If file name is enclosed in '"' remove these and look only in '.' */
983-
/* Informix does look into all include paths though, except filename starts with '/' */
984-
if ((yytext[0] == '"' && yytext[i] == '"') && (compat != ECPG_COMPAT_INFORMIX || yytext[0] == '/'))
985-
{
986-
yytext[i] = '\0';
987-
memmove(yytext, yytext+1, strlen(yytext));
988-
989-
strncpy(inc_file, yytext, sizeof(inc_file));
990-
yyin = fopen(inc_file, "r");
991-
if (!yyin)
992-
{
993-
if (strcmp(inc_file + strlen(inc_file) - 2, ".h"))
994-
{
995-
strcat(inc_file, ".h");
996-
yyin = fopen(inc_file, "r");
997-
}
998-
}
999-
1000-
}
1001-
else
1002-
{
1003-
if (yytext[0] == '"' && yytext[i] == '"')
1004-
{
1005-
yytext[i] = '\0';
1006-
memmove(yytext, yytext+1, strlen(yytext));
1007-
}
1008-
1009-
for (ip = include_paths; yyin == NULL && ip != NULL; ip = ip->next)
1010-
{
1011-
if (strlen(ip->path) + strlen(yytext) + 3 > MAXPGPATH)
1012-
{
1013-
fprintf(stderr, "Error: Path %s/%s is too long in line %d, skipping.\n", ip->path, yytext, yylineno);
1014-
continue;
1015-
}
1016-
snprintf (inc_file, sizeof(inc_file), "%s/%s", ip->path, yytext);
1017-
yyin = fopen(inc_file, "r");
1018-
if (!yyin)
1019-
{
1020-
if (strcmp(inc_file + strlen(inc_file) - 2, ".h"))
1021-
{
1022-
strcat(inc_file, ".h");
1023-
yyin = fopen( inc_file, "r" );
1024-
}
1025-
}
1026-
}
1027-
}
1028-
if (!yyin)
1029-
{
1030-
snprintf(errortext, sizeof(errortext), "Cannot open include file %s in line %d\n", yytext, yylineno);
1031-
mmerror(NO_INCLUDE_FILE, ET_FATAL, errortext);
1032-
}
1033-
1034-
input_filename = mm_strdup(inc_file);
1035-
yy_switch_to_buffer(yy_create_buffer(yyin,YY_BUF_SIZE ));
1036-
yylineno = 1;
1037-
output_line_number();
1038-
1039-
BEGIN C;
1040-
#endif
1041-
}
953+
<incl>[^;\<\>\"]+";" { parse_include(); }
1042954

1043955
<<EOF>> {
1044956
if (yy_buffer == NULL) {

src/interfaces/ecpg/preproc/preproc.y

Lines changed: 75 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/* $Header: /cvsroot/pgsql/src/interfaces/ecpg/preproc/Attic/preproc.y,v 1.223 2003/05/27 11:31:52 meskes Exp $ */
1+
/* $Header: /cvsroot/pgsql/src/interfaces/ecpg/preproc/Attic/preproc.y,v 1.224 2003/05/29 12:00:21 meskes Exp $ */
22

33
/* Copyright comment */
44
%{
@@ -27,6 +27,9 @@ struct ECPGstruct_member *struct_member_list[STRUCT_DEPTH] = { NULL };
2727
/* also store struct type so we can do a sizeof() later */
2828
static char *ECPGstruct_sizeof = NULL;
2929

30+
/* for forward declarations we have to store some data as well */
31+
static char *forward_name = NULL;
32+
3033
struct ECPGtype ecpg_no_indicator = {ECPGt_NO_INDICATOR, 0L, NULL, {NULL}};
3134
struct variable no_indicator = {"no_indicator", &ecpg_no_indicator, 0, NULL};
3235

@@ -196,6 +199,7 @@ create_questionmarks(char *name, bool array)
196199
enum ECPGttype type_enum;
197200
enum ECPGdtype dtype_enum;
198201
struct fetch_desc descriptor;
202+
struct su_symbol struct_union;
199203
}
200204

201205
/* special embedded SQL token */
@@ -440,7 +444,9 @@ create_questionmarks(char *name, bool array)
440444
%type <str> reserved_keyword unreserved_keyword ecpg_interval
441445
%type <str> col_name_keyword func_name_keyword precision opt_scale
442446
%type <str> ECPGTypeName variablelist ECPGColLabelCommon c_variable
443-
%type <str> s_struct_union_symbol inf_val_list inf_col_list
447+
%type <str> inf_val_list inf_col_list
448+
449+
%type <struct_union> s_struct_union_symbol
444450

445451
%type <descriptor> ECPGGetDescriptor
446452

@@ -4039,7 +4045,6 @@ connection_target: database_name opt_server opt_port
40394045
}
40404046
| StringConst
40414047
{
4042-
printf("MM: %s\n", $1);
40434048
if ($1[0] == '\"')
40444049
$$ = $1;
40454050
else if (strcmp($1, " ?") == 0) /* variable */
@@ -4425,16 +4430,34 @@ single_vt_type: common_type
44254430
| s_struct_union_symbol
44264431
{
44274432
/* this is for named structs/unions */
4428-
char *name = $1;
4429-
struct typedefs *this = get_typedef(name);
4430-
4431-
$$.type_str = mm_strdup(this->name);
4432-
$$.type_enum = this->type->type_enum;
4433-
$$.type_dimension = this->type->type_dimension;
4434-
$$.type_index = this->type->type_index;
4435-
$$.type_sizeof = this->type->type_sizeof;
4436-
struct_member_list[struct_level] = ECPGstruct_member_dup(this->struct_member_list);
4437-
free(name);
4433+
char *name;
4434+
struct typedefs *this;
4435+
bool forward = (strcmp($1.symbol, forward_name) == 0 && strcmp($1.su, "struct") == 0);
4436+
4437+
name = cat2_str($1.su, $1.symbol);
4438+
/* Do we have a forward definition? */
4439+
if (!forward)
4440+
{
4441+
/* No */
4442+
4443+
this = get_typedef(name);
4444+
$$.type_str = mm_strdup(this->name);
4445+
$$.type_enum = this->type->type_enum;
4446+
$$.type_dimension = this->type->type_dimension;
4447+
$$.type_index = this->type->type_index;
4448+
$$.type_sizeof = this->type->type_sizeof;
4449+
struct_member_list[struct_level] = ECPGstruct_member_dup(this->struct_member_list);
4450+
free(name);
4451+
}
4452+
else
4453+
{
4454+
$$.type_str = name;
4455+
$$.type_enum = ECPGt_long;
4456+
$$.type_dimension = make_str("-1");
4457+
$$.type_index = make_str("-1");
4458+
$$.type_sizeof = make_str("");
4459+
struct_member_list[struct_level] = NULL;
4460+
}
44384461
}
44394462
;
44404463

@@ -4761,15 +4784,34 @@ var_type: common_type
47614784
| s_struct_union_symbol
47624785
{
47634786
/* this is for named structs/unions */
4764-
char *name = $1;
4765-
struct typedefs *this = get_typedef(name);
4766-
$$.type_str = mm_strdup(this->name);
4767-
$$.type_enum = this->type->type_enum;
4768-
$$.type_dimension = this->type->type_dimension;
4769-
$$.type_index = this->type->type_index;
4770-
$$.type_sizeof = this->type->type_sizeof;
4771-
struct_member_list[struct_level] = ECPGstruct_member_dup(this->struct_member_list);
4772-
free(name);
4787+
char *name;
4788+
struct typedefs *this;
4789+
bool forward = (strcmp($1.symbol, forward_name) == 0 && strcmp($1.su, "struct") == 0);
4790+
4791+
name = cat2_str($1.su, $1.symbol);
4792+
/* Do we have a forward definition? */
4793+
if (!forward)
4794+
{
4795+
/* No */
4796+
4797+
this = get_typedef(name);
4798+
$$.type_str = mm_strdup(this->name);
4799+
$$.type_enum = this->type->type_enum;
4800+
$$.type_dimension = this->type->type_dimension;
4801+
$$.type_index = this->type->type_index;
4802+
$$.type_sizeof = this->type->type_sizeof;
4803+
struct_member_list[struct_level] = ECPGstruct_member_dup(this->struct_member_list);
4804+
free(name);
4805+
}
4806+
else
4807+
{
4808+
$$.type_str = name;
4809+
$$.type_enum = ECPGt_long;
4810+
$$.type_dimension = make_str("-1");
4811+
$$.type_index = make_str("-1");
4812+
$$.type_sizeof = make_str("");
4813+
struct_member_list[struct_level] = NULL;
4814+
}
47734815
}
47744816
;
47754817

@@ -4789,18 +4831,21 @@ struct_union_type_with_symbol: s_struct_union_symbol
47894831
struct_member_list[struct_level++] = NULL;
47904832
if (struct_level >= STRUCT_DEPTH)
47914833
mmerror(PARSE_ERROR, ET_ERROR, "Too many levels in nested structure/union definition");
4834+
forward_name = mm_strdup($1.symbol);
47924835
}
47934836
'{' variable_declarations '}'
47944837
{
47954838
ECPGfree_struct_member(struct_member_list[struct_level]);
47964839
struct_member_list[struct_level] = NULL;
47974840
free(actual_storage[struct_level--]);
4798-
if (strncmp($1, "struct", sizeof("struct")-1) == 0)
4841+
if (strncmp($1.su, "struct", sizeof("struct")-1) == 0)
47994842
$$.type_enum = ECPGt_struct;
48004843
else
48014844
$$.type_enum = ECPGt_union;
4802-
$$.type_str = mm_strdup($1);
4803-
$$.type_sizeof = cat_str(4, $1, make_str("{"), $4, make_str("}"));
4845+
$$.type_str = cat2_str($1.su, $1.symbol);
4846+
$$.type_sizeof = cat_str(4, mm_strdup($$.type_str), make_str("{"), $4, make_str("}"));
4847+
free(forward_name);
4848+
forward_name = NULL;
48044849
}
48054850
;
48064851

@@ -4822,12 +4867,14 @@ struct_union_type: struct_union_type_with_symbol { $$ = $1.type_sizeof; }
48224867

48234868
s_struct_union_symbol: SQL_STRUCT symbol
48244869
{
4825-
$$ = cat2_str(make_str("struct"), $2);
4826-
ECPGstruct_sizeof = cat_str(3, make_str("sizeof("), strdup($$), make_str(")"));
4870+
$$.su = make_str("struct");
4871+
$$.symbol = $2;
4872+
ECPGstruct_sizeof = cat_str(3, make_str("sizeof("), cat2_str(mm_strdup($$.su), mm_strdup($$.symbol)), make_str(")"));
48274873
}
48284874
| UNION symbol
48294875
{
4830-
$$ = cat2_str(make_str("union"), $2);
4876+
$$.su = make_str("union");
4877+
$$.symbol = $2;
48314878
}
48324879
;
48334880

src/interfaces/ecpg/preproc/type.c

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -225,16 +225,21 @@ ECPGdump_a_type(FILE *o, const char *name, struct ECPGtype * type,
225225
case ECPGt_array:
226226
if (indicator_set && ind_type->type != ECPGt_array)
227227
mmerror(INDICATOR_NOT_ARRAY, ET_FATAL, "Indicator for array/pointer has to be array/pointer.\n");
228-
229228
switch (type->u.element->type)
230229
{
231230
case ECPGt_array:
232231
mmerror(PARSE_ERROR, ET_ERROR, "No nested arrays allowed (except strings)"); /* array of array */
233232
break;
234233
case ECPGt_struct:
235234
case ECPGt_union:
236-
/* If var_array_element is not equal * NULL, we have to use the * <var_array_element>th entry and not * the whole array */ if (var_array_element == NULL)
237-
ECPGdump_a_struct(o, name, ind_name, type->size,
235+
/* If var_array_element is not equal
236+
* NULL, we have to use the
237+
* <var_array_element>th entry and
238+
* not the whole array */
239+
if (var_array_element == NULL)
240+
ECPGdump_a_struct(o, name,
241+
ind_name,
242+
type->size,
238243
type->u.element,
239244
(ind_type->type == ECPGt_NO_INDICATOR) ? ind_type : ind_type->u.element,
240245
NULL, prefix, ind_prefix);

src/interfaces/ecpg/preproc/type.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,12 @@ struct index
8888
char *str;
8989
};
9090

91+
struct su_symbol
92+
{
93+
char *su;
94+
char *symbol;
95+
};
96+
9197
struct this_type
9298
{
9399
enum ECPGttype type_enum;

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy