@@ -12,7 +12,11 @@ static void yyerror(char *);
1212/*
1313 * Variables containing simple states.
1414*/
15- int debugging =0 ;
15+ int debugging =0 ;
16+ static int struct_level =0 ;
17+
18+ /* temporarily store record members while creating the data structure*/
19+ struct ECPGrecord_member *record_member_list[128 ] = {NULL };
1620
1721/*
1822 * Handle the filename and line numbering.
@@ -86,7 +90,7 @@ remove_variables(int brace_level)
8690{
8791struct variable * p, *prev;
8892
89- for (p = prev = allvariables; p; p = p->next )
93+ for (p = prev = allvariables; p; p = p ? p ->next : NULL )
9094 {
9195if (p->brace_level >= brace_level)
9296{
@@ -96,6 +100,8 @@ remove_variables(int brace_level)
96100else
97101prev->next = p->next ;
98102
103+ ECPGfree_type (p->type );
104+ free (p->name );
99105free (p);
100106 p = prev;
101107}
@@ -157,7 +163,7 @@ dump_variables(struct arguments * list)
157163dump_variables (list->next );
158164
159165/* Then the current element.*/
160- ECPGdump_a_type (yyout, list->variable ->name , list->variable ->type );
166+ ECPGdump_a_type (yyout, list->variable ->name , list->variable ->type , NULL );
161167
162168/* Then release the list element.*/
163169free (list);
@@ -179,12 +185,12 @@ dump_variables(struct arguments * list)
179185
180186%token <tagname> S_SYMBOL S_LENGTH S_ANYTHING
181187%token <tagname> S_VARCHAR S_VARCHAR2
182- %token <tagname> S_EXTERN S_STATIC
188+ %token <tagname> S_EXTERN S_STATIC S_AUTO S_CONST S_REGISTER S_STRUCT
183189%token <tagname> S_UNSIGNED S_SIGNED
184190%token <tagname> S_LONG S_SHORT S_INT S_CHAR S_FLOAT S_DOUBLE S_BOOL
185191%token <tagname> ' [' ' ]' ' ;' ' ,' ' {' ' }'
186192
187- %type <type> type type_detailed varchar_type simple_type array_type
193+ %type <type> type type_detailed varchar_type simple_type array_type struct_type
188194%type <symbolname> symbol
189195%type <tagname> maybe_storage_clause varchar_tag
190196%type <type_enum> simple_tag
@@ -227,8 +233,12 @@ variable_declarations : /* empty */
227233
228234/* Here is where we can enter support for typedef.*/
229235variable_declaration :type ' ;' {
230- new_variable ($<type>1 .name, $<type>1 .typ);
231- free ($<type>1 .name);
236+ /* don't worry about our list when we're working on a struct*/
237+ if (struct_level ==0 )
238+ {
239+ new_variable ($<type>1 .name, $<type>1 .typ);
240+ free ($<type>1 .name);
241+ }
232242fprintf (yyout," ;" );
233243}
234244
@@ -244,27 +254,61 @@ symbol : S_SYMBOL {
244254type :maybe_storage_clause type_detailed { $<type>$ = $<type>2 ; };
245255type_detailed :varchar_type { $<type>$ = $<type>1 ; }
246256| simple_type { $<type>$ = $<type>1 ; }
247- | array_type {$<type>$ = $<type>1 ; };
257+ | array_type {$<type>$ = $<type>1 ; }
258+ | struct_type {$<type>$ = $<type>1 ; };
248259
249260varchar_type :varchar_tag symbol index {
250261fprintf (yyout," struct varchar_%s { int len; char arr[%d]; } %s" , $<symbolname>2 , $<indexsize>3 , $<symbolname>2 );
251- $<type>$.name = $<symbolname>2 ;
252- $<type>$.typ = ECPGmake_varchar_type(ECPGt_varchar, $<indexsize>3 );
262+ if (struct_level ==0 )
263+ {
264+ $<type>$.name = $<symbolname>2 ;
265+ $<type>$.typ = ECPGmake_varchar_type(ECPGt_varchar, $<indexsize>3 );
266+ }
267+ else
268+ ECPGmake_record_member ($<symbolname>2 , ECPGmake_varchar_type(ECPGt_varchar, $<indexsize>3 ), &(record_member_list[struct_level-1 ]));
253269}
254270
255271varchar_tag :S_VARCHAR { $<tagname>$ = $<tagname>1 ; }
256272| S_VARCHAR2 { $<tagname>$ = $<tagname>1 ; };
257273
258274simple_type :simple_tag symbol {
259275fprintf (yyout," %s %s" , ECPGtype_name($<type_enum>1 ), $<symbolname>2);
260- $<type>$.name = $<symbolname>2 ;
261- $<type>$.typ = ECPGmake_simple_type($<type_enum>1 );
276+ if (struct_level ==0 )
277+ {
278+ $<type>$.name = $<symbolname>2 ;
279+ $<type>$.typ = ECPGmake_simple_type($<type_enum>1 );
280+ }
281+ else
282+ ECPGmake_record_member ($<symbolname>2 , ECPGmake_simple_type($<type_enum>1 ), &(record_member_list[struct_level-1 ]));
262283}
263284
264285array_type :simple_tag symbol index {
265286fprintf (yyout," %s %s [%d]" , ECPGtype_name($<type_enum>1 ), $<symbolname>2, $<indexsize>3);
266- $<type>$.name = $<symbolname>2 ;
267- $<type>$.typ = ECPGmake_array_type(ECPGmake_simple_type($<type_enum>1 ), $<indexsize>3 );
287+ if (struct_level ==0 )
288+ {
289+ $<type>$.name = $<symbolname>2 ;
290+ $<type>$.typ = ECPGmake_array_type(ECPGmake_simple_type($<type_enum>1 ), $<indexsize>3 );
291+ }
292+ else
293+ ECPGmake_record_member ($<symbolname>2 , ECPGmake_array_type(ECPGmake_simple_type($<type_enum>1 ), $<indexsize>3), &(record_member_list[struct_level-1 ]));
294+ }
295+
296+ s_struct :S_STRUCT symbol {
297+ struct_level++;
298+ fprintf (yyout," struct %s {" , $<symbolname>2 );
299+ }
300+
301+ struct_type :s_struct ' {' variable_declarations ' }' symbol {
302+ struct_level--;
303+ if (struct_level ==0 )
304+ {
305+ $<type>$.name = $<symbolname>5 ;
306+ $<type>$.typ = ECPGmake_record_type(record_member_list[struct_level]);
307+ }
308+ else
309+ ECPGmake_record_member ($<symbolname>5 , ECPGmake_record_type(record_member_list[struct_level]), &(record_member_list[struct_level-1 ]));
310+ fprintf (yyout," } %s" , $<symbolname>5 );
311+ record_member_list[struct_level] =NULL ;
268312}
269313
270314simple_tag :S_CHAR { $<type_enum>$ = ECPGt_char; }
@@ -281,6 +325,9 @@ simple_tag : S_CHAR { $<type_enum>$ = ECPGt_char; }
281325
282326maybe_storage_clause :S_EXTERN { fwrite(yytext, yyleng,1 , yyout); }
283327| S_STATIC { fwrite(yytext, yyleng,1 , yyout); }
328+ | S_CONST { fwrite(yytext, yyleng,1 , yyout); }
329+ | S_REGISTER { fwrite(yytext, yyleng,1 , yyout); }
330+ | S_AUTO { fwrite(yytext, yyleng,1 , yyout); }
284331| /* empty*/ { };
285332
286333index :' [' length ' ]' {
@@ -369,13 +416,14 @@ canything : both_anything
369416sqlanything :both_anything ;
370417
371418both_anything :S_LENGTH | S_VARCHAR | S_VARCHAR2
372- | S_LONG | S_SHORT | S_INT | S_CHAR | S_FLOAT | S_DOUBLE
419+ | S_LONG | S_SHORT | S_INT | S_CHAR | S_FLOAT | S_DOUBLE | S_BOOL
373420| SQL_OPEN | SQL_CONNECT
374421| SQL_STRING
375422| SQL_BEGIN | SQL_END
376423| SQL_DECLARE | SQL_SECTION
377424| SQL_INCLUDE
378425| S_SYMBOL
426+ | S_STATIC | S_EXTERN | S_AUTO | S_CONST | S_REGISTER | S_STRUCT
379427| ' [' | ' ]' | ' ,'
380428| S_ANYTHING ;
381429